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 17 package com.android.server.wifi; 18 19 import static android.net.wifi.WifiConfiguration.MeteredOverride; 20 21 import static com.android.server.wifi.ActiveModeManager.ROLE_CLIENT_PRIMARY; 22 import static com.android.server.wifi.proto.WifiStatsLog.WIFI_CONFIG_SAVED; 23 import static com.android.server.wifi.proto.WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED; 24 25 import static java.lang.StrictMath.toIntExact; 26 27 import android.annotation.IntDef; 28 import android.annotation.NonNull; 29 import android.annotation.Nullable; 30 import android.app.ActivityManager; 31 import android.content.Context; 32 import android.content.Intent; 33 import android.content.pm.PackageManager; 34 import android.content.pm.ResolveInfo; 35 import android.net.NetworkCapabilities; 36 import android.net.wifi.EAPConstants; 37 import android.net.wifi.IOnWifiUsabilityStatsListener; 38 import android.net.wifi.MloLink; 39 import android.net.wifi.ScanResult; 40 import android.net.wifi.SecurityParams; 41 import android.net.wifi.SoftApCapability; 42 import android.net.wifi.SoftApConfiguration; 43 import android.net.wifi.SoftApInfo; 44 import android.net.wifi.SupplicantState; 45 import android.net.wifi.WifiAnnotations; 46 import android.net.wifi.WifiConfiguration; 47 import android.net.wifi.WifiConfiguration.NetworkSelectionStatus; 48 import android.net.wifi.WifiEnterpriseConfig; 49 import android.net.wifi.WifiInfo; 50 import android.net.wifi.WifiManager; 51 import android.net.wifi.WifiManager.DeviceMobilityState; 52 import android.net.wifi.WifiScanner; 53 import android.net.wifi.WifiUsabilityStatsEntry.ProbeStatus; 54 import android.net.wifi.hotspot2.PasspointConfiguration; 55 import android.net.wifi.hotspot2.ProvisioningCallback; 56 import android.net.wifi.hotspot2.ProvisioningCallback.OsuFailure; 57 import android.net.wifi.nl80211.WifiNl80211Manager; 58 import android.net.wifi.util.ScanResultUtil; 59 import android.os.Handler; 60 import android.os.Looper; 61 import android.os.Message; 62 import android.os.Process; 63 import android.os.RemoteCallbackList; 64 import android.os.RemoteException; 65 import android.os.SystemProperties; 66 import android.os.WorkSource; 67 import android.provider.Settings; 68 import android.telephony.TelephonyManager; 69 import android.text.TextUtils; 70 import android.util.ArrayMap; 71 import android.util.ArraySet; 72 import android.util.Base64; 73 import android.util.Log; 74 import android.util.Pair; 75 import android.util.SparseArray; 76 import android.util.SparseBooleanArray; 77 import android.util.SparseIntArray; 78 79 import com.android.internal.annotations.VisibleForTesting; 80 import com.android.server.wifi.SupplicantStaIfaceHal.StaIfaceReasonCode; 81 import com.android.server.wifi.SupplicantStaIfaceHal.StaIfaceStatusCode; 82 import com.android.server.wifi.aware.WifiAwareMetrics; 83 import com.android.server.wifi.hotspot2.ANQPNetworkKey; 84 import com.android.server.wifi.hotspot2.NetworkDetail; 85 import com.android.server.wifi.hotspot2.PasspointManager; 86 import com.android.server.wifi.hotspot2.PasspointMatch; 87 import com.android.server.wifi.hotspot2.PasspointProvider; 88 import com.android.server.wifi.hotspot2.Utils; 89 import com.android.server.wifi.p2p.WifiP2pMetrics; 90 import com.android.server.wifi.proto.WifiStatsLog; 91 import com.android.server.wifi.proto.nano.WifiMetricsProto; 92 import com.android.server.wifi.proto.nano.WifiMetricsProto.ConnectToNetworkNotificationAndActionCount; 93 import com.android.server.wifi.proto.nano.WifiMetricsProto.ContentionTimeStats; 94 import com.android.server.wifi.proto.nano.WifiMetricsProto.DeviceMobilityStatePnoScanStats; 95 import com.android.server.wifi.proto.nano.WifiMetricsProto.ExperimentValues; 96 import com.android.server.wifi.proto.nano.WifiMetricsProto.FirstConnectAfterBootStats; 97 import com.android.server.wifi.proto.nano.WifiMetricsProto.FirstConnectAfterBootStats.Attempt; 98 import com.android.server.wifi.proto.nano.WifiMetricsProto.HealthMonitorMetrics; 99 import com.android.server.wifi.proto.nano.WifiMetricsProto.InitPartialScanStats; 100 import com.android.server.wifi.proto.nano.WifiMetricsProto.LinkProbeStats; 101 import com.android.server.wifi.proto.nano.WifiMetricsProto.LinkProbeStats.ExperimentProbeCounts; 102 import com.android.server.wifi.proto.nano.WifiMetricsProto.LinkProbeStats.LinkProbeFailureReasonCount; 103 import com.android.server.wifi.proto.nano.WifiMetricsProto.LinkSpeedCount; 104 import com.android.server.wifi.proto.nano.WifiMetricsProto.MeteredNetworkStats; 105 import com.android.server.wifi.proto.nano.WifiMetricsProto.NetworkDisableReason; 106 import com.android.server.wifi.proto.nano.WifiMetricsProto.NetworkSelectionExperimentDecisions; 107 import com.android.server.wifi.proto.nano.WifiMetricsProto.PasspointProfileTypeCount; 108 import com.android.server.wifi.proto.nano.WifiMetricsProto.PasspointProvisionStats; 109 import com.android.server.wifi.proto.nano.WifiMetricsProto.PasspointProvisionStats.ProvisionFailureCount; 110 import com.android.server.wifi.proto.nano.WifiMetricsProto.PnoScanMetrics; 111 import com.android.server.wifi.proto.nano.WifiMetricsProto.RadioStats; 112 import com.android.server.wifi.proto.nano.WifiMetricsProto.RateStats; 113 import com.android.server.wifi.proto.nano.WifiMetricsProto.SoftApConnectedClientsEvent; 114 import com.android.server.wifi.proto.nano.WifiMetricsProto.StaEvent; 115 import com.android.server.wifi.proto.nano.WifiMetricsProto.StaEvent.ConfigInfo; 116 import com.android.server.wifi.proto.nano.WifiMetricsProto.TargetNetworkInfo; 117 import com.android.server.wifi.proto.nano.WifiMetricsProto.UserActionEvent; 118 import com.android.server.wifi.proto.nano.WifiMetricsProto.UserReactionToApprovalUiEvent; 119 import com.android.server.wifi.proto.nano.WifiMetricsProto.UserReactionToApprovalUiEvent.UserReaction; 120 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiIsUnusableEvent; 121 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiLinkLayerUsageStats; 122 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiLockStats; 123 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiNetworkRequestApiLog; 124 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiNetworkSuggestionApiLog; 125 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiNetworkSuggestionApiLog.SuggestionAppCount; 126 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiStatus; 127 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiToWifiSwitchStats; 128 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiToggleStats; 129 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiUsabilityStats; 130 import com.android.server.wifi.proto.nano.WifiMetricsProto.WifiUsabilityStatsEntry; 131 import com.android.server.wifi.rtt.RttMetrics; 132 import com.android.server.wifi.scanner.KnownBandsChannelHelper; 133 import com.android.server.wifi.util.InformationElementUtil; 134 import com.android.server.wifi.util.InformationElementUtil.ApType6GHz; 135 import com.android.server.wifi.util.InformationElementUtil.WifiMode; 136 import com.android.server.wifi.util.IntCounter; 137 import com.android.server.wifi.util.IntHistogram; 138 import com.android.server.wifi.util.MetricsUtils; 139 import com.android.server.wifi.util.ObjectCounter; 140 import com.android.server.wifi.util.StringUtil; 141 import com.android.wifi.resources.R; 142 143 import org.json.JSONArray; 144 import org.json.JSONException; 145 import org.json.JSONObject; 146 147 import java.io.FileDescriptor; 148 import java.io.PrintWriter; 149 import java.time.Duration; 150 import java.util.ArrayDeque; 151 import java.util.ArrayList; 152 import java.util.Arrays; 153 import java.util.BitSet; 154 import java.util.Calendar; 155 import java.util.Deque; 156 import java.util.HashMap; 157 import java.util.HashSet; 158 import java.util.LinkedList; 159 import java.util.List; 160 import java.util.Map; 161 import java.util.Random; 162 import java.util.Set; 163 164 /** 165 * Provides storage for wireless connectivity metrics, as they are generated. 166 * Metrics logged by this class include: 167 * Aggregated connection stats (num of connections, num of failures, ...) 168 * Discrete connection event stats (time, duration, failure codes, ...) 169 * Router details (technology type, authentication type, ...) 170 * Scan stats 171 */ 172 public class WifiMetrics { 173 private static final String TAG = "WifiMetrics"; 174 private static final boolean DBG = false; 175 176 /** 177 * Clamp the RSSI poll counts to values between [MIN,MAX]_RSSI_POLL 178 */ 179 private static final int MAX_RSSI_POLL = 0; 180 private static final int MIN_RSSI_POLL = -127; 181 public static final int MAX_RSSI_DELTA = 127; 182 public static final int MIN_RSSI_DELTA = -127; 183 /** Minimum link speed (Mbps) to count for link_speed_counts */ 184 public static final int MIN_LINK_SPEED_MBPS = 0; 185 /** Maximum time period between ScanResult and RSSI poll to generate rssi delta datapoint */ 186 public static final long TIMEOUT_RSSI_DELTA_MILLIS = 3000; 187 private static final int MIN_WIFI_SCORE = 0; 188 private static final int MAX_WIFI_SCORE = ConnectedScore.WIFI_MAX_SCORE; 189 private static final int MIN_WIFI_USABILITY_SCORE = 0; // inclusive 190 private static final int MAX_WIFI_USABILITY_SCORE = 100; // inclusive 191 @VisibleForTesting 192 static final int LOW_WIFI_SCORE = 50; // Mobile data score 193 @VisibleForTesting 194 static final int LOW_WIFI_USABILITY_SCORE = 50; // Mobile data score 195 private final Object mLock = new Object(); 196 private static final int MAX_CONNECTION_EVENTS = 256; 197 // Largest bucket in the NumConnectableNetworkCount histogram, 198 // anything large will be stored in this bucket 199 public static final int MAX_CONNECTABLE_SSID_NETWORK_BUCKET = 20; 200 public static final int MAX_CONNECTABLE_BSSID_NETWORK_BUCKET = 50; 201 public static final int MAX_TOTAL_SCAN_RESULT_SSIDS_BUCKET = 100; 202 public static final int MAX_TOTAL_SCAN_RESULTS_BUCKET = 250; 203 public static final int MAX_TOTAL_PASSPOINT_APS_BUCKET = 50; 204 public static final int MAX_TOTAL_PASSPOINT_UNIQUE_ESS_BUCKET = 20; 205 public static final int MAX_PASSPOINT_APS_PER_UNIQUE_ESS_BUCKET = 50; 206 public static final int MAX_TOTAL_80211MC_APS_BUCKET = 20; 207 private static final int CONNECT_TO_NETWORK_NOTIFICATION_ACTION_KEY_MULTIPLIER = 1000; 208 // Max limit for number of soft AP related events, extra events will be dropped. 209 private static final int MAX_NUM_SOFT_AP_EVENTS = 256; 210 // Maximum number of WifiIsUnusableEvent 211 public static final int MAX_UNUSABLE_EVENTS = 20; 212 // Minimum time wait before generating next WifiIsUnusableEvent from data stall 213 public static final int MIN_DATA_STALL_WAIT_MS = 120 * 1000; // 2 minutes 214 // Max number of WifiUsabilityStatsEntry elements to store in the ringbuffer. 215 public static final int MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE = 40; 216 // Max number of WifiUsabilityStats elements to store for each type. 217 public static final int MAX_WIFI_USABILITY_STATS_LIST_SIZE_PER_TYPE = 10; 218 // Max number of WifiUsabilityStats per labeled type to upload to server 219 public static final int MAX_WIFI_USABILITY_STATS_PER_TYPE_TO_UPLOAD = 2; 220 public static final int NUM_WIFI_USABILITY_STATS_ENTRIES_PER_WIFI_GOOD = 100; 221 public static final int MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS = 1000 * 3600; // 1 hour 222 public static final int PASSPOINT_DEAUTH_IMMINENT_SCOPE_ESS = 0; 223 public static final int PASSPOINT_DEAUTH_IMMINENT_SCOPE_BSS = 1; 224 public static final int COUNTRY_CODE_CONFLICT_WIFI_SCAN = -1; 225 public static final int COUNTRY_CODE_CONFLICT_WIFI_SCAN_TELEPHONY = -2; 226 public static final int MAX_COUNTRY_CODE_COUNT = 4; 227 // Histogram for WifiConfigStore IO duration times. Indicates the following 5 buckets (in ms): 228 // < 50 229 // [50, 100) 230 // [100, 150) 231 // [150, 200) 232 // [200, 300) 233 // >= 300 234 private static final int[] WIFI_CONFIG_STORE_IO_DURATION_BUCKET_RANGES_MS = 235 {50, 100, 150, 200, 300}; 236 // Minimum time wait before generating a LABEL_GOOD stats after score breaching low. 237 public static final int MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS = 60 * 1000; // 1 minute 238 // Maximum time that a score breaching low event stays valid. 239 public static final int VALIDITY_PERIOD_OF_SCORE_BREACH_LOW_MS = 90 * 1000; // 1.5 minutes 240 241 private static final int WIFI_RECONNECT_DURATION_SHORT_MILLIS = 10 * 1000; 242 private static final int WIFI_RECONNECT_DURATION_MEDIUM_MILLIS = 60 * 1000; 243 // Number of WME Access Categories 244 private static final int NUM_WME_ACCESS_CATEGORIES = 4; 245 private static final int MBB_LINGERING_DURATION_MAX_SECONDS = 30; 246 247 private Clock mClock; 248 private boolean mScreenOn; 249 private int mWifiState; 250 private WifiAwareMetrics mWifiAwareMetrics; 251 private RttMetrics mRttMetrics; 252 private final PnoScanMetrics mPnoScanMetrics = new PnoScanMetrics(); 253 private final WifiLinkLayerUsageStats mWifiLinkLayerUsageStats = new WifiLinkLayerUsageStats(); 254 /** Mapping of radio id values to RadioStats objects. */ 255 private final SparseArray<RadioStats> mRadioStats = new SparseArray<>(); 256 private final ExperimentValues mExperimentValues = new ExperimentValues(); 257 private Handler mHandler; 258 private ScoringParams mScoringParams; 259 private WifiConfigManager mWifiConfigManager; 260 private WifiBlocklistMonitor mWifiBlocklistMonitor; 261 private WifiNetworkSelector mWifiNetworkSelector; 262 private PasspointManager mPasspointManager; 263 private Context mContext; 264 private FrameworkFacade mFacade; 265 private WifiDataStall mWifiDataStall; 266 private WifiLinkLayerStats mLastLinkLayerStats; 267 private WifiHealthMonitor mWifiHealthMonitor; 268 private WifiScoreCard mWifiScoreCard; 269 private SessionData mPreviousSession; 270 private SessionData mCurrentSession; 271 private String mLastBssid; 272 private int mLastFrequency = -1; 273 private int mSeqNumInsideFramework = 0; 274 private int mLastWifiUsabilityScore = -1; 275 private int mLastWifiUsabilityScoreNoReset = -1; 276 private int mLastPredictionHorizonSec = -1; 277 private int mLastPredictionHorizonSecNoReset = -1; 278 private int mSeqNumToFramework = -1; 279 @ProbeStatus private int mProbeStatusSinceLastUpdate = 280 android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE; 281 private int mProbeElapsedTimeSinceLastUpdateMs = -1; 282 private int mProbeMcsRateSinceLastUpdate = -1; 283 private long mScoreBreachLowTimeMillis = -1; 284 285 public static final int MAX_STA_EVENTS = 768; 286 @VisibleForTesting static final int MAX_USER_ACTION_EVENTS = 200; 287 private LinkedList<StaEventWithTime> mStaEventList = new LinkedList<>(); 288 private LinkedList<UserActionEventWithTime> mUserActionEventList = new LinkedList<>(); 289 private WifiStatusBuilder mWifiStatusBuilder = new WifiStatusBuilder(); 290 private int mLastPollRssi = -127; 291 private int mLastPollLinkSpeed = -1; 292 private int mLastPollRxLinkSpeed = -1; 293 private int mLastPollFreq = -1; 294 private int mLastScore = -1; 295 private boolean mAdaptiveConnectivityEnabled = true; 296 private ScanMetrics mScanMetrics; 297 private WifiChannelUtilization mWifiChannelUtilization; 298 private WifiSettingsStore mWifiSettingsStore; 299 private IntCounter mPasspointDeauthImminentScope = new IntCounter(); 300 private IntCounter mRecentFailureAssociationStatus = new IntCounter(); 301 private boolean mFirstConnectionAfterBoot = true; 302 private long mLastTotalBeaconRx = 0; 303 private int mScorerUid = Process.WIFI_UID; 304 305 /** 306 * Wi-Fi usability state per interface as predicted by the network scorer. 307 */ 308 public enum WifiUsabilityState {UNKNOWN, USABLE, UNUSABLE}; 309 private final Map<String, WifiUsabilityState> mWifiUsabilityStatePerIface = new ArrayMap<>(); 310 311 /** 312 * Metrics are stored within an instance of the WifiLog proto during runtime, 313 * The ConnectionEvent, SystemStateEntries & ScanReturnEntries metrics are stored during 314 * runtime in member lists of this WifiMetrics class, with the final WifiLog proto being pieced 315 * together at dump-time 316 */ 317 private final WifiMetricsProto.WifiLog mWifiLogProto = new WifiMetricsProto.WifiLog(); 318 /** 319 * Session information that gets logged for every Wifi connection attempt. 320 */ 321 private final Deque<ConnectionEvent> mConnectionEventList = new ArrayDeque<>(); 322 /** 323 * The latest started (but un-ended) connection attempt per interface. 324 */ 325 private final Map<String, ConnectionEvent> mCurrentConnectionEventPerIface = new ArrayMap<>(); 326 /** 327 * Count of number of times each scan return code, indexed by WifiLog.ScanReturnCode 328 */ 329 private final SparseIntArray mScanReturnEntries = new SparseIntArray(); 330 /** 331 * Mapping of system state to the counts of scans requested in that wifi state * screenOn 332 * combination. Indexed by WifiLog.WifiState * (1 + screenOn) 333 */ 334 private final SparseIntArray mWifiSystemStateEntries = new SparseIntArray(); 335 /** Mapping of channel frequency to its RSSI distribution histogram **/ 336 private final Map<Integer, SparseIntArray> mRssiPollCountsMap = new HashMap<>(); 337 /** Mapping of RSSI scan-poll delta values to counts. */ 338 private final SparseIntArray mRssiDeltaCounts = new SparseIntArray(); 339 /** Mapping of link speed values to LinkSpeedCount objects. */ 340 private final SparseArray<LinkSpeedCount> mLinkSpeedCounts = new SparseArray<>(); 341 342 private final IntCounter mTxLinkSpeedCount2g = new IntCounter(); 343 private final IntCounter mTxLinkSpeedCount5gLow = new IntCounter(); 344 private final IntCounter mTxLinkSpeedCount5gMid = new IntCounter(); 345 private final IntCounter mTxLinkSpeedCount5gHigh = new IntCounter(); 346 private final IntCounter mTxLinkSpeedCount6gLow = new IntCounter(); 347 private final IntCounter mTxLinkSpeedCount6gMid = new IntCounter(); 348 private final IntCounter mTxLinkSpeedCount6gHigh = new IntCounter(); 349 350 private final IntCounter mRxLinkSpeedCount2g = new IntCounter(); 351 private final IntCounter mRxLinkSpeedCount5gLow = new IntCounter(); 352 private final IntCounter mRxLinkSpeedCount5gMid = new IntCounter(); 353 private final IntCounter mRxLinkSpeedCount5gHigh = new IntCounter(); 354 private final IntCounter mRxLinkSpeedCount6gLow = new IntCounter(); 355 private final IntCounter mRxLinkSpeedCount6gMid = new IntCounter(); 356 private final IntCounter mRxLinkSpeedCount6gHigh = new IntCounter(); 357 358 private final IntCounter mMakeBeforeBreakLingeringDurationSeconds = new IntCounter(); 359 360 /** RSSI of the scan result for the last connection event*/ 361 private int mScanResultRssi = 0; 362 /** Boot-relative timestamp when the last candidate scanresult was received, used to calculate 363 RSSI deltas. -1 designates no candidate scanResult being tracked */ 364 private long mScanResultRssiTimestampMillis = -1; 365 /** Mapping of alert reason to the respective alert count. */ 366 private final SparseIntArray mWifiAlertReasonCounts = new SparseIntArray(); 367 /** 368 * Records the getElapsedSinceBootMillis (in seconds) that represents the beginning of data 369 * capture for for this WifiMetricsProto 370 */ 371 private long mRecordStartTimeSec; 372 /** Mapping of Wifi Scores to counts */ 373 private final SparseIntArray mWifiScoreCounts = new SparseIntArray(); 374 /** Mapping of Wifi Usability Scores to counts */ 375 private final SparseIntArray mWifiUsabilityScoreCounts = new SparseIntArray(); 376 /** Mapping of SoftApManager start SoftAp return codes to counts */ 377 private final SparseIntArray mSoftApManagerReturnCodeCounts = new SparseIntArray(); 378 379 private final SparseIntArray mTotalSsidsInScanHistogram = new SparseIntArray(); 380 private final SparseIntArray mTotalBssidsInScanHistogram = new SparseIntArray(); 381 private final SparseIntArray mAvailableOpenSsidsInScanHistogram = new SparseIntArray(); 382 private final SparseIntArray mAvailableOpenBssidsInScanHistogram = new SparseIntArray(); 383 private final SparseIntArray mAvailableSavedSsidsInScanHistogram = new SparseIntArray(); 384 private final SparseIntArray mAvailableSavedBssidsInScanHistogram = new SparseIntArray(); 385 private final SparseIntArray mAvailableOpenOrSavedSsidsInScanHistogram = new SparseIntArray(); 386 private final SparseIntArray mAvailableOpenOrSavedBssidsInScanHistogram = new SparseIntArray(); 387 private final SparseIntArray mAvailableSavedPasspointProviderProfilesInScanHistogram = 388 new SparseIntArray(); 389 private final SparseIntArray mAvailableSavedPasspointProviderBssidsInScanHistogram = 390 new SparseIntArray(); 391 392 private final IntCounter mInstalledPasspointProfileTypeForR1 = new IntCounter(); 393 private final IntCounter mInstalledPasspointProfileTypeForR2 = new IntCounter(); 394 395 /** Mapping of "Connect to Network" notifications to counts. */ 396 private final SparseIntArray mConnectToNetworkNotificationCount = new SparseIntArray(); 397 /** Mapping of "Connect to Network" notification user actions to counts. */ 398 private final SparseIntArray mConnectToNetworkNotificationActionCount = new SparseIntArray(); 399 private int mOpenNetworkRecommenderBlocklistSize = 0; 400 private boolean mIsWifiNetworksAvailableNotificationOn = false; 401 private int mNumOpenNetworkConnectMessageFailedToSend = 0; 402 private int mNumOpenNetworkRecommendationUpdates = 0; 403 /** List of soft AP events related to number of connected clients in tethered mode */ 404 private final List<SoftApConnectedClientsEvent> mSoftApEventListTethered = new ArrayList<>(); 405 /** List of soft AP events related to number of connected clients in local only mode */ 406 private final List<SoftApConnectedClientsEvent> mSoftApEventListLocalOnly = new ArrayList<>(); 407 408 private final SparseIntArray mObservedHotspotR1ApInScanHistogram = new SparseIntArray(); 409 private final SparseIntArray mObservedHotspotR2ApInScanHistogram = new SparseIntArray(); 410 private final SparseIntArray mObservedHotspotR3ApInScanHistogram = new SparseIntArray(); 411 private final SparseIntArray mObservedHotspotR1EssInScanHistogram = new SparseIntArray(); 412 private final SparseIntArray mObservedHotspotR2EssInScanHistogram = new SparseIntArray(); 413 private final SparseIntArray mObservedHotspotR3EssInScanHistogram = new SparseIntArray(); 414 private final SparseIntArray mObservedHotspotR1ApsPerEssInScanHistogram = new SparseIntArray(); 415 private final SparseIntArray mObservedHotspotR2ApsPerEssInScanHistogram = new SparseIntArray(); 416 private final SparseIntArray mObservedHotspotR3ApsPerEssInScanHistogram = new SparseIntArray(); 417 418 private final SparseIntArray mObserved80211mcApInScanHistogram = new SparseIntArray(); 419 420 // link probing stats 421 private final IntCounter mLinkProbeSuccessRssiCounts = new IntCounter(-85, -65); 422 private final IntCounter mLinkProbeFailureRssiCounts = new IntCounter(-85, -65); 423 private final IntCounter mLinkProbeSuccessLinkSpeedCounts = new IntCounter(); 424 private final IntCounter mLinkProbeFailureLinkSpeedCounts = new IntCounter(); 425 426 private static final int[] LINK_PROBE_TIME_SINCE_LAST_TX_SUCCESS_SECONDS_HISTOGRAM_BUCKETS = 427 {5, 15, 45, 135}; 428 private final IntHistogram mLinkProbeSuccessSecondsSinceLastTxSuccessHistogram = 429 new IntHistogram(LINK_PROBE_TIME_SINCE_LAST_TX_SUCCESS_SECONDS_HISTOGRAM_BUCKETS); 430 private final IntHistogram mLinkProbeFailureSecondsSinceLastTxSuccessHistogram = 431 new IntHistogram(LINK_PROBE_TIME_SINCE_LAST_TX_SUCCESS_SECONDS_HISTOGRAM_BUCKETS); 432 433 private static final int[] LINK_PROBE_ELAPSED_TIME_MS_HISTOGRAM_BUCKETS = 434 {5, 10, 15, 20, 25, 50, 100, 200, 400, 800}; 435 private final IntHistogram mLinkProbeSuccessElapsedTimeMsHistogram = new IntHistogram( 436 LINK_PROBE_ELAPSED_TIME_MS_HISTOGRAM_BUCKETS); 437 private final IntCounter mLinkProbeFailureReasonCounts = new IntCounter(); 438 private final MeteredNetworkStatsBuilder mMeteredNetworkStatsBuilder = 439 new MeteredNetworkStatsBuilder(); 440 441 /** 442 * Maps a String link probe experiment ID to the number of link probes that were sent for this 443 * experiment. 444 */ 445 private final ObjectCounter<String> mLinkProbeExperimentProbeCounts = new ObjectCounter<>(); 446 private int mLinkProbeStaEventCount = 0; 447 @VisibleForTesting static final int MAX_LINK_PROBE_STA_EVENTS = MAX_STA_EVENTS / 4; 448 449 private final LinkedList<WifiUsabilityStatsEntry> mWifiUsabilityStatsEntriesList = 450 new LinkedList<>(); 451 private final LinkedList<WifiUsabilityStats> mWifiUsabilityStatsListBad = new LinkedList<>(); 452 private final LinkedList<WifiUsabilityStats> mWifiUsabilityStatsListGood = new LinkedList<>(); 453 private int mWifiUsabilityStatsCounter = 0; 454 private final Random mRand = new Random(); 455 private final RemoteCallbackList<IOnWifiUsabilityStatsListener> mOnWifiUsabilityListeners; 456 457 private final SparseArray<DeviceMobilityStatePnoScanStats> mMobilityStatePnoStatsMap = 458 new SparseArray<>(); 459 private int mCurrentDeviceMobilityState; 460 /** 461 * The timestamp of the start of the current device mobility state. 462 */ 463 private long mCurrentDeviceMobilityStateStartMs; 464 /** 465 * The timestamp of when the PNO scan started in the current device mobility state. 466 */ 467 private long mCurrentDeviceMobilityStatePnoScanStartMs; 468 469 /** Wifi power metrics*/ 470 private WifiPowerMetrics mWifiPowerMetrics; 471 472 /** Wifi Wake metrics */ 473 private final WifiWakeMetrics mWifiWakeMetrics = new WifiWakeMetrics(); 474 475 /** Wifi P2p metrics */ 476 private final WifiP2pMetrics mWifiP2pMetrics; 477 478 /** DPP */ 479 private final DppMetrics mDppMetrics; 480 481 private final WifiMonitor mWifiMonitor; 482 private ActiveModeWarden mActiveModeWarden; 483 private final Map<String, ActiveModeManager.ClientRole> mIfaceToRoleMap = new ArrayMap<>(); 484 485 /** WifiConfigStore read duration histogram. */ 486 private SparseIntArray mWifiConfigStoreReadDurationHistogram = new SparseIntArray(); 487 488 /** WifiConfigStore write duration histogram. */ 489 private SparseIntArray mWifiConfigStoreWriteDurationHistogram = new SparseIntArray(); 490 491 /** New API surface metrics */ 492 private final WifiNetworkRequestApiLog mWifiNetworkRequestApiLog = 493 new WifiNetworkRequestApiLog(); 494 private static final int[] NETWORK_REQUEST_API_MATCH_SIZE_HISTOGRAM_BUCKETS = 495 {0, 1, 5, 10}; 496 private final IntHistogram mWifiNetworkRequestApiMatchSizeHistogram = 497 new IntHistogram(NETWORK_REQUEST_API_MATCH_SIZE_HISTOGRAM_BUCKETS); 498 499 private static final int[] NETWORK_REQUEST_API_DURATION_SEC_BUCKETS = 500 {0, toIntExact(Duration.ofMinutes(3).getSeconds()), 501 toIntExact(Duration.ofMinutes(10).getSeconds()), 502 toIntExact(Duration.ofMinutes(30).getSeconds()), 503 toIntExact(Duration.ofHours(1).getSeconds()), 504 toIntExact(Duration.ofHours(6).getSeconds())}; 505 private final IntHistogram mWifiNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram = 506 new IntHistogram(NETWORK_REQUEST_API_DURATION_SEC_BUCKETS); 507 private final IntHistogram 508 mWifiNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram = 509 new IntHistogram(NETWORK_REQUEST_API_DURATION_SEC_BUCKETS); 510 private final IntHistogram mWifiNetworkRequestApiConcurrentConnectionDurationSecHistogram = 511 new IntHistogram(NETWORK_REQUEST_API_DURATION_SEC_BUCKETS); 512 513 private final WifiNetworkSuggestionApiLog mWifiNetworkSuggestionApiLog = 514 new WifiNetworkSuggestionApiLog(); 515 private static final int[] NETWORK_SUGGESTION_API_LIST_SIZE_HISTOGRAM_BUCKETS = 516 {5, 20, 50, 100, 500}; 517 private final IntHistogram mWifiNetworkSuggestionApiListSizeHistogram = 518 new IntHistogram(NETWORK_SUGGESTION_API_LIST_SIZE_HISTOGRAM_BUCKETS); 519 private final IntCounter mWifiNetworkSuggestionApiAppTypeCounter = new IntCounter(); 520 private final List<UserReaction> mUserApprovalSuggestionAppUiReactionList = 521 new ArrayList<>(); 522 private final List<UserReaction> mUserApprovalCarrierUiReactionList = 523 new ArrayList<>(); 524 private final SparseBooleanArray mWifiNetworkSuggestionPriorityGroups = 525 new SparseBooleanArray(); 526 private final Set<String> mWifiNetworkSuggestionCoexistSavedNetworks = new ArraySet<>(); 527 528 private final WifiLockStats mWifiLockStats = new WifiLockStats(); 529 private static final int[] WIFI_LOCK_SESSION_DURATION_HISTOGRAM_BUCKETS = 530 {1, 10, 60, 600, 3600}; 531 private final WifiToggleStats mWifiToggleStats = new WifiToggleStats(); 532 private BssidBlocklistStats mBssidBlocklistStats = new BssidBlocklistStats(); 533 534 private final IntHistogram mWifiLockHighPerfAcqDurationSecHistogram = 535 new IntHistogram(WIFI_LOCK_SESSION_DURATION_HISTOGRAM_BUCKETS); 536 private final IntHistogram mWifiLockLowLatencyAcqDurationSecHistogram = 537 new IntHistogram(WIFI_LOCK_SESSION_DURATION_HISTOGRAM_BUCKETS); 538 539 private final IntHistogram mWifiLockHighPerfActiveSessionDurationSecHistogram = 540 new IntHistogram(WIFI_LOCK_SESSION_DURATION_HISTOGRAM_BUCKETS); 541 private final IntHistogram mWifiLockLowLatencyActiveSessionDurationSecHistogram = 542 new IntHistogram(WIFI_LOCK_SESSION_DURATION_HISTOGRAM_BUCKETS); 543 544 /** 545 * (experiment1Id, experiment2Id) => 546 * (sameSelectionNumChoicesCounter, differentSelectionNumChoicesCounter) 547 */ 548 private Map<Pair<Integer, Integer>, NetworkSelectionExperimentResults> 549 mNetworkSelectionExperimentPairNumChoicesCounts = new ArrayMap<>(); 550 551 private int mNetworkSelectorExperimentId; 552 553 /** 554 * Tracks the nominator for each network (i.e. which entity made the suggestion to connect). 555 * This object should not be cleared. 556 */ 557 private final SparseIntArray mNetworkIdToNominatorId = new SparseIntArray(); 558 559 /** passpoint provision success count */ 560 private int mNumProvisionSuccess = 0; 561 562 /** Mapping of failure code to the respective passpoint provision failure count. */ 563 private final IntCounter mPasspointProvisionFailureCounts = new IntCounter(); 564 565 // Connection duration stats collected while link layer stats reports are on 566 private final ConnectionDurationStats mConnectionDurationStats = new ConnectionDurationStats(); 567 568 private static final int[] CHANNEL_UTILIZATION_BUCKETS = 569 {25, 50, 75, 100, 125, 150, 175, 200, 225}; 570 571 private final IntHistogram mChannelUtilizationHistogram2G = 572 new IntHistogram(CHANNEL_UTILIZATION_BUCKETS); 573 574 private final IntHistogram mChannelUtilizationHistogramAbove2G = 575 new IntHistogram(CHANNEL_UTILIZATION_BUCKETS); 576 577 private static final int[] THROUGHPUT_MBPS_BUCKETS = 578 {1, 5, 10, 15, 25, 50, 100, 150, 200, 300, 450, 600, 800, 1200, 1600}; 579 private final IntHistogram mTxThroughputMbpsHistogram2G = 580 new IntHistogram(THROUGHPUT_MBPS_BUCKETS); 581 private final IntHistogram mRxThroughputMbpsHistogram2G = 582 new IntHistogram(THROUGHPUT_MBPS_BUCKETS); 583 private final IntHistogram mTxThroughputMbpsHistogramAbove2G = 584 new IntHistogram(THROUGHPUT_MBPS_BUCKETS); 585 private final IntHistogram mRxThroughputMbpsHistogramAbove2G = 586 new IntHistogram(THROUGHPUT_MBPS_BUCKETS); 587 588 // Init partial scan metrics 589 private int mInitPartialScanTotalCount; 590 private int mInitPartialScanSuccessCount; 591 private int mInitPartialScanFailureCount; 592 private static final int[] INIT_PARTIAL_SCAN_HISTOGRAM_BUCKETS = 593 {1, 3, 5, 10}; 594 private final IntHistogram mInitPartialScanSuccessHistogram = 595 new IntHistogram(INIT_PARTIAL_SCAN_HISTOGRAM_BUCKETS); 596 private final IntHistogram mInitPartialScanFailureHistogram = 597 new IntHistogram(INIT_PARTIAL_SCAN_HISTOGRAM_BUCKETS); 598 599 // Wi-Fi off metrics 600 private final WifiOffMetrics mWifiOffMetrics = new WifiOffMetrics(); 601 602 private final SoftApConfigLimitationMetrics mSoftApConfigLimitationMetrics = 603 new SoftApConfigLimitationMetrics(); 604 605 private final CarrierWifiMetrics mCarrierWifiMetrics = 606 new CarrierWifiMetrics(); 607 608 @Nullable 609 private FirstConnectAfterBootStats mFirstConnectAfterBootStats = 610 new FirstConnectAfterBootStats(); 611 private boolean mIsFirstConnectionAttemptComplete = false; 612 613 private final WifiToWifiSwitchStats mWifiToWifiSwitchStats = new WifiToWifiSwitchStats(); 614 615 /** Wi-Fi link specific metrics (MLO). */ 616 public static class LinkMetrics { 617 private long mTotalBeaconRx = 0; 618 private @android.net.wifi.WifiUsabilityStatsEntry.LinkState int mLinkUsageState = 619 android.net.wifi.WifiUsabilityStatsEntry.LINK_STATE_UNKNOWN; 620 621 /** Get Total beacon received on this link */ getTotalBeaconRx()622 public long getTotalBeaconRx() { 623 return mTotalBeaconRx; 624 } 625 626 /** Set Total beacon received on this link */ setTotalBeaconRx(long totalBeaconRx)627 public void setTotalBeaconRx(long totalBeaconRx) { 628 this.mTotalBeaconRx = totalBeaconRx; 629 } 630 631 /** Get link usage state */ getLinkUsageState()632 public @android.net.wifi.WifiUsabilityStatsEntry.LinkState int getLinkUsageState() { 633 return mLinkUsageState; 634 } 635 636 /** Set link usage state */ setLinkUsageState( @ndroid.net.wifi.WifiUsabilityStatsEntry.LinkState int linkUsageState)637 public void setLinkUsageState( 638 @android.net.wifi.WifiUsabilityStatsEntry.LinkState int linkUsageState) { 639 this.mLinkUsageState = linkUsageState; 640 } 641 } 642 643 public SparseArray<LinkMetrics> mLastLinkMetrics = new SparseArray<>(); 644 645 @VisibleForTesting 646 static class NetworkSelectionExperimentResults { 647 public static final int MAX_CHOICES = 10; 648 649 public IntCounter sameSelectionNumChoicesCounter = new IntCounter(0, MAX_CHOICES); 650 public IntCounter differentSelectionNumChoicesCounter = new IntCounter(0, MAX_CHOICES); 651 652 @Override toString()653 public String toString() { 654 return "NetworkSelectionExperimentResults{" 655 + "sameSelectionNumChoicesCounter=" 656 + sameSelectionNumChoicesCounter 657 + ", differentSelectionNumChoicesCounter=" 658 + differentSelectionNumChoicesCounter 659 + '}'; 660 } 661 } 662 663 private static class SessionData { 664 private String mSsid; 665 private long mSessionStartTimeMillis; 666 private long mSessionEndTimeMillis; 667 private int mBand; 668 private int mAuthType; 669 private ConnectionEvent mConnectionEvent; 670 private long mLastRoamCompleteMillis; 671 SessionData(ConnectionEvent connectionEvent, String ssid, long sessionStartTimeMillis, int band, int authType)672 SessionData(ConnectionEvent connectionEvent, String ssid, long sessionStartTimeMillis, 673 int band, int authType) { 674 mConnectionEvent = connectionEvent; 675 mSsid = ssid; 676 mSessionStartTimeMillis = sessionStartTimeMillis; 677 mBand = band; 678 mAuthType = authType; 679 mLastRoamCompleteMillis = sessionStartTimeMillis; 680 } 681 } 682 683 /** 684 * Sets the timestamp after roaming is complete. 685 */ onRoamComplete()686 public void onRoamComplete() { 687 if (mCurrentSession != null) { 688 mCurrentSession.mLastRoamCompleteMillis = mClock.getElapsedSinceBootMillis(); 689 } 690 } 691 692 class RouterFingerPrint { 693 private final WifiMetricsProto.RouterFingerPrint mRouterFingerPrintProto = 694 new WifiMetricsProto.RouterFingerPrint(); 695 // Additional parameters which is not captured in WifiMetricsProto.RouterFingerPrint. 696 private boolean mIsFrameworkInitiatedRoaming = false; 697 private @WifiConfiguration.SecurityType int mSecurityMode = 698 WifiConfiguration.SECURITY_TYPE_OPEN; 699 private boolean mIsIncorrectlyConfiguredAsHidden = false; 700 private int mWifiStandard = WifiMode.MODE_UNDEFINED; 701 private boolean mIs11bSupported = false; 702 private boolean mIsMboSupported = false; 703 private boolean mIsOceSupported = false; 704 private boolean mIsFilsSupported = false; 705 private boolean mIsIndividualTwtSupported = false; 706 private boolean mIsBroadcastTwtSupported = false; 707 private boolean mIsRestrictedTwtSupported = false; 708 private boolean mIsTwtRequired = false; 709 private boolean mIs11AzSupported = false; 710 private boolean mIs11McSupported = false; 711 private boolean mIsEcpsPriorityAccessSupported = false; 712 private NetworkDetail.HSRelease mHsRelease = NetworkDetail.HSRelease.Unknown; 713 private ApType6GHz mApType6GHz = ApType6GHz.AP_TYPE_6GHZ_UNKNOWN; 714 public @WifiAnnotations.ChannelWidth int mChannelWidth = ScanResult.UNSPECIFIED; 715 toString()716 public String toString() { 717 StringBuilder sb = new StringBuilder(); 718 synchronized (mLock) { 719 sb.append("mConnectionEvent.roamType=" + mRouterFingerPrintProto.roamType); 720 sb.append(", mChannelInfo=" + mRouterFingerPrintProto.channelInfo); 721 sb.append(", mDtim=" + mRouterFingerPrintProto.dtim); 722 sb.append(", mAuthentication=" + mRouterFingerPrintProto.authentication); 723 sb.append(", mHidden=" + mRouterFingerPrintProto.hidden); 724 sb.append(", mRouterTechnology=" + mRouterFingerPrintProto.routerTechnology); 725 sb.append(", mSupportsIpv6=" + mRouterFingerPrintProto.supportsIpv6); 726 sb.append(", mEapMethod=" + mRouterFingerPrintProto.eapMethod); 727 sb.append(", mAuthPhase2Method=" + mRouterFingerPrintProto.authPhase2Method); 728 sb.append(", mOcspType=" + mRouterFingerPrintProto.ocspType); 729 sb.append(", mPmkCache=" + mRouterFingerPrintProto.pmkCacheEnabled); 730 sb.append(", mMaxSupportedTxLinkSpeedMbps=" + mRouterFingerPrintProto 731 .maxSupportedTxLinkSpeedMbps); 732 sb.append(", mMaxSupportedRxLinkSpeedMbps=" + mRouterFingerPrintProto 733 .maxSupportedRxLinkSpeedMbps); 734 sb.append(", mIsFrameworkInitiatedRoaming=" + mIsFrameworkInitiatedRoaming); 735 sb.append(", mIsIncorrectlyConfiguredAsHidden=" + mIsIncorrectlyConfiguredAsHidden); 736 sb.append(", mWifiStandard=" + mWifiStandard); 737 sb.append(", mIs11bSupported=" + mIs11bSupported); 738 sb.append(", mIsMboSupported=" + mIsMboSupported); 739 sb.append(", mIsOceSupported=" + mIsOceSupported); 740 sb.append(", mIsFilsSupported=" + mIsFilsSupported); 741 sb.append(", mIsIndividualTwtSupported=" + mIsIndividualTwtSupported); 742 sb.append(", mIsBroadcastTwtSupported=" + mIsBroadcastTwtSupported); 743 sb.append(", mIsRestrictedTwtSupported=" + mIsRestrictedTwtSupported); 744 sb.append(", mIsTwtRequired=" + mIsTwtRequired); 745 sb.append(", mIs11mcSupported=" + mIs11McSupported); 746 sb.append(", mIs11azSupported=" + mIs11AzSupported); 747 sb.append(", mApType6Ghz=" + mApType6GHz); 748 sb.append(", mIsEcpsPriorityAccessSupported=" + mIsEcpsPriorityAccessSupported); 749 sb.append(", mHsRelease=" + mHsRelease); 750 sb.append(", mChannelWidth" + mChannelWidth); 751 } 752 return sb.toString(); 753 } 754 setPmkCache(boolean isEnabled)755 public void setPmkCache(boolean isEnabled) { 756 synchronized (mLock) { 757 mRouterFingerPrintProto.pmkCacheEnabled = isEnabled; 758 } 759 } 760 setMaxSupportedLinkSpeedMbps(int maxSupportedTxLinkSpeedMbps, int maxSupportedRxLinkSpeedMbps)761 public void setMaxSupportedLinkSpeedMbps(int maxSupportedTxLinkSpeedMbps, 762 int maxSupportedRxLinkSpeedMbps) { 763 synchronized (mLock) { 764 mRouterFingerPrintProto.maxSupportedTxLinkSpeedMbps = maxSupportedTxLinkSpeedMbps; 765 mRouterFingerPrintProto.maxSupportedRxLinkSpeedMbps = maxSupportedRxLinkSpeedMbps; 766 } 767 } 768 } getEapMethodProto(int eapMethod)769 private int getEapMethodProto(int eapMethod) { 770 switch (eapMethod) { 771 case WifiEnterpriseConfig.Eap.WAPI_CERT: 772 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_WAPI_CERT; 773 case WifiEnterpriseConfig.Eap.TLS: 774 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_TLS; 775 case WifiEnterpriseConfig.Eap.UNAUTH_TLS: 776 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_UNAUTH_TLS; 777 case WifiEnterpriseConfig.Eap.PEAP: 778 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_PEAP; 779 case WifiEnterpriseConfig.Eap.PWD: 780 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_PWD; 781 case WifiEnterpriseConfig.Eap.TTLS: 782 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_TTLS; 783 case WifiEnterpriseConfig.Eap.SIM: 784 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_SIM; 785 case WifiEnterpriseConfig.Eap.AKA: 786 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_AKA; 787 case WifiEnterpriseConfig.Eap.AKA_PRIME: 788 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_AKA_PRIME; 789 default: 790 return WifiMetricsProto.RouterFingerPrint.TYPE_EAP_UNKNOWN; 791 } 792 } 793 getAuthPhase2MethodProto(int phase2Method)794 private static int getAuthPhase2MethodProto(int phase2Method) { 795 switch (phase2Method) { 796 case WifiEnterpriseConfig.Phase2.PAP: 797 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_PAP; 798 case WifiEnterpriseConfig.Phase2.MSCHAP: 799 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_MSCHAP; 800 case WifiEnterpriseConfig.Phase2.MSCHAPV2: 801 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_MSCHAPV2; 802 case WifiEnterpriseConfig.Phase2.GTC: 803 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_GTC; 804 case WifiEnterpriseConfig.Phase2.SIM: 805 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_SIM; 806 case WifiEnterpriseConfig.Phase2.AKA: 807 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_AKA; 808 case WifiEnterpriseConfig.Phase2.AKA_PRIME: 809 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_AKA_PRIME; 810 default: 811 return WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_NONE; 812 } 813 } 814 getOcspTypeProto(int ocspType)815 private int getOcspTypeProto(int ocspType) { 816 switch (ocspType) { 817 case WifiEnterpriseConfig.OCSP_NONE: 818 return WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_NONE; 819 case WifiEnterpriseConfig.OCSP_REQUEST_CERT_STATUS: 820 return WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_REQUEST_CERT_STATUS; 821 case WifiEnterpriseConfig.OCSP_REQUIRE_CERT_STATUS: 822 return WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_REQUIRE_CERT_STATUS; 823 case WifiEnterpriseConfig.OCSP_REQUIRE_ALL_NON_TRUSTED_CERTS_STATUS: 824 return WifiMetricsProto.RouterFingerPrint 825 .TYPE_OCSP_REQUIRE_ALL_NON_TRUSTED_CERTS_STATUS; 826 default: 827 return WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_NONE; 828 } 829 } 830 831 class BssidBlocklistStats { 832 public IntCounter networkSelectionFilteredBssidCount = new IntCounter(); 833 public int numHighMovementConnectionSkipped = 0; 834 public int numHighMovementConnectionStarted = 0; 835 private final IntCounter mBlockedBssidPerReasonCount = new IntCounter(); 836 private final IntCounter mBlockedConfigurationPerReasonCount = new IntCounter(); 837 toProto()838 public WifiMetricsProto.BssidBlocklistStats toProto() { 839 WifiMetricsProto.BssidBlocklistStats proto = new WifiMetricsProto.BssidBlocklistStats(); 840 proto.networkSelectionFilteredBssidCount = networkSelectionFilteredBssidCount.toProto(); 841 proto.highMovementMultipleScansFeatureEnabled = mContext.getResources().getBoolean( 842 R.bool.config_wifiHighMovementNetworkSelectionOptimizationEnabled); 843 proto.numHighMovementConnectionSkipped = numHighMovementConnectionSkipped; 844 proto.numHighMovementConnectionStarted = numHighMovementConnectionStarted; 845 proto.bssidBlocklistPerReasonCount = mBlockedBssidPerReasonCount.toProto(); 846 proto.wifiConfigBlocklistPerReasonCount = mBlockedConfigurationPerReasonCount.toProto(); 847 return proto; 848 } 849 incrementBssidBlocklistCount(int blockReason)850 public void incrementBssidBlocklistCount(int blockReason) { 851 mBlockedBssidPerReasonCount.increment(blockReason); 852 } 853 incrementWificonfigurationBlocklistCount(int blockReason)854 public void incrementWificonfigurationBlocklistCount(int blockReason) { 855 mBlockedConfigurationPerReasonCount.increment(blockReason); 856 } 857 858 @Override toString()859 public String toString() { 860 StringBuilder sb = new StringBuilder(); 861 sb.append("networkSelectionFilteredBssidCount=" + networkSelectionFilteredBssidCount); 862 sb.append("\nmBlockedBssidPerReasonCount=" + mBlockedBssidPerReasonCount); 863 sb.append("\nmBlockedConfigurationPerReasonCount=" 864 + mBlockedConfigurationPerReasonCount); 865 866 sb.append(", highMovementMultipleScansFeatureEnabled=" 867 + mContext.getResources().getBoolean( 868 R.bool.config_wifiHighMovementNetworkSelectionOptimizationEnabled)); 869 sb.append(", numHighMovementConnectionSkipped=" + numHighMovementConnectionSkipped); 870 sb.append(", numHighMovementConnectionStarted=" + numHighMovementConnectionStarted); 871 sb.append(", mBlockedBssidPerReasonCount=" + mBlockedBssidPerReasonCount); 872 sb.append(", mBlockedConfigurationPerReasonCount=" 873 + mBlockedConfigurationPerReasonCount); 874 return sb.toString(); 875 } 876 } 877 878 class ConnectionDurationStats { 879 private int mConnectionDurationCellularDataOffMs; 880 private int mConnectionDurationSufficientThroughputMs; 881 private int mConnectionDurationInSufficientThroughputMs; 882 private int mConnectionDurationInSufficientThroughputDefaultWifiMs; 883 toProto()884 public WifiMetricsProto.ConnectionDurationStats toProto() { 885 WifiMetricsProto.ConnectionDurationStats proto = 886 new WifiMetricsProto.ConnectionDurationStats(); 887 proto.totalTimeSufficientThroughputMs = mConnectionDurationSufficientThroughputMs; 888 proto.totalTimeInsufficientThroughputMs = mConnectionDurationInSufficientThroughputMs; 889 proto.totalTimeInsufficientThroughputDefaultWifiMs = 890 mConnectionDurationInSufficientThroughputDefaultWifiMs; 891 proto.totalTimeCellularDataOffMs = mConnectionDurationCellularDataOffMs; 892 return proto; 893 } clear()894 public void clear() { 895 mConnectionDurationCellularDataOffMs = 0; 896 mConnectionDurationSufficientThroughputMs = 0; 897 mConnectionDurationInSufficientThroughputMs = 0; 898 mConnectionDurationInSufficientThroughputDefaultWifiMs = 0; 899 } incrementDurationCount(int timeDeltaLastTwoPollsMs, boolean isThroughputSufficient, boolean isCellularDataAvailable, boolean isDefaultOnWifi)900 public void incrementDurationCount(int timeDeltaLastTwoPollsMs, 901 boolean isThroughputSufficient, boolean isCellularDataAvailable, 902 boolean isDefaultOnWifi) { 903 if (!isCellularDataAvailable) { 904 mConnectionDurationCellularDataOffMs += timeDeltaLastTwoPollsMs; 905 } else { 906 if (isThroughputSufficient) { 907 mConnectionDurationSufficientThroughputMs += timeDeltaLastTwoPollsMs; 908 } else { 909 mConnectionDurationInSufficientThroughputMs += timeDeltaLastTwoPollsMs; 910 if (isDefaultOnWifi) { 911 mConnectionDurationInSufficientThroughputDefaultWifiMs += 912 timeDeltaLastTwoPollsMs; 913 } 914 } 915 } 916 } 917 @Override toString()918 public String toString() { 919 StringBuilder sb = new StringBuilder(); 920 sb.append("connectionDurationSufficientThroughputMs=") 921 .append(mConnectionDurationSufficientThroughputMs) 922 .append(", connectionDurationInSufficientThroughputMs=") 923 .append(mConnectionDurationInSufficientThroughputMs) 924 .append(", connectionDurationInSufficientThroughputDefaultWifiMs=") 925 .append(mConnectionDurationInSufficientThroughputDefaultWifiMs) 926 .append(", connectionDurationCellularDataOffMs=") 927 .append(mConnectionDurationCellularDataOffMs); 928 return sb.toString(); 929 } 930 } 931 932 class WifiStatusBuilder { 933 private int mNetworkId = WifiConfiguration.INVALID_NETWORK_ID; 934 private boolean mConnected; 935 private boolean mValidated; 936 private int mRssi; 937 private int mEstimatedTxKbps; 938 private int mEstimatedRxKbps; 939 private boolean mIsStuckDueToUserChoice; 940 setNetworkId(int networkId)941 public void setNetworkId(int networkId) { 942 mNetworkId = networkId; 943 } 944 getNetworkId()945 public int getNetworkId() { 946 return mNetworkId; 947 } 948 setConnected(boolean connected)949 public void setConnected(boolean connected) { 950 mConnected = connected; 951 } 952 setValidated(boolean validated)953 public void setValidated(boolean validated) { 954 mValidated = validated; 955 } 956 setRssi(int rssi)957 public void setRssi(int rssi) { 958 mRssi = rssi; 959 } 960 setEstimatedTxKbps(int estimatedTxKbps)961 public void setEstimatedTxKbps(int estimatedTxKbps) { 962 mEstimatedTxKbps = estimatedTxKbps; 963 } 964 setEstimatedRxKbps(int estimatedRxKbps)965 public void setEstimatedRxKbps(int estimatedRxKbps) { 966 mEstimatedRxKbps = estimatedRxKbps; 967 } 968 setUserChoice(boolean userChoice)969 public void setUserChoice(boolean userChoice) { 970 mIsStuckDueToUserChoice = userChoice; 971 } 972 toProto()973 public WifiStatus toProto() { 974 WifiStatus result = new WifiStatus(); 975 result.isConnected = mConnected; 976 result.isValidated = mValidated; 977 result.lastRssi = mRssi; 978 result.estimatedTxKbps = mEstimatedTxKbps; 979 result.estimatedRxKbps = mEstimatedRxKbps; 980 result.isStuckDueToUserConnectChoice = mIsStuckDueToUserChoice; 981 return result; 982 } 983 } 984 convertToNetworkDisableReason( WifiConfiguration config, Set<Integer> bssidBlocklistReasons)985 private NetworkDisableReason convertToNetworkDisableReason( 986 WifiConfiguration config, Set<Integer> bssidBlocklistReasons) { 987 NetworkSelectionStatus status = config.getNetworkSelectionStatus(); 988 NetworkDisableReason result = new NetworkDisableReason(); 989 if (config.allowAutojoin) { 990 if (!status.isNetworkEnabled()) { 991 result.disableReason = 992 MetricsUtils.convertNetworkSelectionDisableReasonToWifiProtoEnum( 993 status.getNetworkSelectionDisableReason()); 994 if (status.isNetworkPermanentlyDisabled()) { 995 result.configPermanentlyDisabled = true; 996 } else { 997 result.configTemporarilyDisabled = true; 998 } 999 } 1000 } else { 1001 result.disableReason = NetworkDisableReason.REASON_AUTO_JOIN_DISABLED; 1002 result.configPermanentlyDisabled = true; 1003 } 1004 1005 int[] convertedBssidBlockReasons = bssidBlocklistReasons.stream() 1006 .mapToInt(i -> MetricsUtils.convertBssidBlocklistReasonToWifiProtoEnum(i)) 1007 .toArray(); 1008 if (convertedBssidBlockReasons.length > 0) { 1009 result.bssidDisableReasons = convertedBssidBlockReasons; 1010 } 1011 return result; 1012 } 1013 1014 class UserActionEventWithTime { 1015 private UserActionEvent mUserActionEvent; 1016 private long mWallClockTimeMs = 0; // wall clock time for debugging only 1017 UserActionEventWithTime(int eventType, TargetNetworkInfo targetNetworkInfo)1018 UserActionEventWithTime(int eventType, TargetNetworkInfo targetNetworkInfo) { 1019 mUserActionEvent = new UserActionEvent(); 1020 mUserActionEvent.eventType = eventType; 1021 mUserActionEvent.startTimeMillis = mClock.getElapsedSinceBootMillis(); 1022 mWallClockTimeMs = mClock.getWallClockMillis(); 1023 mUserActionEvent.targetNetworkInfo = targetNetworkInfo; 1024 mUserActionEvent.wifiStatus = mWifiStatusBuilder.toProto(); 1025 } 1026 UserActionEventWithTime(int eventType, int targetNetId)1027 UserActionEventWithTime(int eventType, int targetNetId) { 1028 this(eventType, null); 1029 if (targetNetId >= 0) { 1030 WifiConfiguration config = mWifiConfigManager.getConfiguredNetwork(targetNetId); 1031 if (config != null) { 1032 TargetNetworkInfo networkInfo = new TargetNetworkInfo(); 1033 networkInfo.isEphemeral = config.isEphemeral(); 1034 networkInfo.isPasspoint = config.isPasspoint(); 1035 mUserActionEvent.targetNetworkInfo = networkInfo; 1036 mUserActionEvent.networkDisableReason = convertToNetworkDisableReason( 1037 config, mWifiBlocklistMonitor.getFailureReasonsForSsid(config.SSID)); 1038 } 1039 } 1040 } 1041 toString()1042 public String toString() { 1043 StringBuilder sb = new StringBuilder(); 1044 Calendar c = Calendar.getInstance(); 1045 c.setTimeInMillis(mWallClockTimeMs); 1046 sb.append(StringUtil.calendarToString(c)); 1047 String eventType = "UNKNOWN"; 1048 switch (mUserActionEvent.eventType) { 1049 case UserActionEvent.EVENT_FORGET_WIFI: 1050 eventType = "EVENT_FORGET_WIFI"; 1051 break; 1052 case UserActionEvent.EVENT_DISCONNECT_WIFI: 1053 eventType = "EVENT_DISCONNECT_WIFI"; 1054 break; 1055 case UserActionEvent.EVENT_CONFIGURE_METERED_STATUS_METERED: 1056 eventType = "EVENT_CONFIGURE_METERED_STATUS_METERED"; 1057 break; 1058 case UserActionEvent.EVENT_CONFIGURE_METERED_STATUS_UNMETERED: 1059 eventType = "EVENT_CONFIGURE_METERED_STATUS_UNMETERED"; 1060 break; 1061 case UserActionEvent.EVENT_CONFIGURE_METERED_STATUS_AUTO: 1062 eventType = "EVENT_CONFIGURE_METERED_STATUS_AUTO"; 1063 break; 1064 case UserActionEvent.EVENT_CONFIGURE_MAC_RANDOMIZATION_ON: 1065 eventType = "EVENT_CONFIGURE_MAC_RANDOMIZATION_ON"; 1066 break; 1067 case UserActionEvent.EVENT_CONFIGURE_MAC_RANDOMIZATION_OFF: 1068 eventType = "EVENT_CONFIGURE_MAC_RANDOMIZATION_OFF"; 1069 break; 1070 case UserActionEvent.EVENT_CONFIGURE_AUTO_CONNECT_ON: 1071 eventType = "EVENT_CONFIGURE_AUTO_CONNECT_ON"; 1072 break; 1073 case UserActionEvent.EVENT_CONFIGURE_AUTO_CONNECT_OFF: 1074 eventType = "EVENT_CONFIGURE_AUTO_CONNECT_OFF"; 1075 break; 1076 case UserActionEvent.EVENT_TOGGLE_WIFI_ON: 1077 eventType = "EVENT_TOGGLE_WIFI_ON"; 1078 break; 1079 case UserActionEvent.EVENT_TOGGLE_WIFI_OFF: 1080 eventType = "EVENT_TOGGLE_WIFI_OFF"; 1081 break; 1082 case UserActionEvent.EVENT_MANUAL_CONNECT: 1083 eventType = "EVENT_MANUAL_CONNECT"; 1084 break; 1085 case UserActionEvent.EVENT_ADD_OR_UPDATE_NETWORK: 1086 eventType = "EVENT_ADD_OR_UPDATE_NETWORK"; 1087 break; 1088 case UserActionEvent.EVENT_RESTART_WIFI_SUB_SYSTEM: 1089 eventType = "EVENT_RESTART_WIFI_SUB_SYSTEM"; 1090 break; 1091 } 1092 sb.append(" eventType=").append(eventType); 1093 sb.append(" startTimeMillis=").append(mUserActionEvent.startTimeMillis); 1094 TargetNetworkInfo networkInfo = mUserActionEvent.targetNetworkInfo; 1095 if (networkInfo != null) { 1096 sb.append(" isEphemeral=").append(networkInfo.isEphemeral); 1097 sb.append(" isPasspoint=").append(networkInfo.isPasspoint); 1098 } 1099 WifiStatus wifiStatus = mUserActionEvent.wifiStatus; 1100 if (wifiStatus != null) { 1101 sb.append("\nWifiStatus: isConnected=").append(wifiStatus.isConnected); 1102 sb.append(" isValidated=").append(wifiStatus.isValidated); 1103 sb.append(" lastRssi=").append(wifiStatus.lastRssi); 1104 sb.append(" estimatedTxKbps=").append(wifiStatus.estimatedTxKbps); 1105 sb.append(" estimatedRxKbps=").append(wifiStatus.estimatedRxKbps); 1106 sb.append(" isStuckDueToUserConnectChoice=") 1107 .append(wifiStatus.isStuckDueToUserConnectChoice); 1108 } 1109 NetworkDisableReason disableReason = mUserActionEvent.networkDisableReason; 1110 if (disableReason != null) { 1111 sb.append("\nNetworkDisableReason: DisableReason=") 1112 .append(disableReason.disableReason); 1113 sb.append(" configTemporarilyDisabled=") 1114 .append(disableReason.configTemporarilyDisabled); 1115 sb.append(" configPermanentlyDisabled=") 1116 .append(disableReason.configPermanentlyDisabled); 1117 sb.append(" bssidDisableReasons=") 1118 .append(Arrays.toString(disableReason.bssidDisableReasons)); 1119 } 1120 return sb.toString(); 1121 } 1122 toProto()1123 public UserActionEvent toProto() { 1124 return mUserActionEvent; 1125 } 1126 } 1127 1128 /** 1129 * Log event, tracking the start time, end time and result of a wireless connection attempt. 1130 */ 1131 class ConnectionEvent { 1132 final WifiMetricsProto.ConnectionEvent mConnectionEvent; 1133 //<TODO> Move these constants into a wifi.proto Enum, and create a new Failure Type field 1134 //covering more than just l2 failures. see b/27652362 1135 /** 1136 * Failure codes, used for the 'level_2_failure_code' Connection event field (covers a lot 1137 * more failures than just l2 though, since the proto does not have a place to log 1138 * framework failures) 1139 */ 1140 // Failure is unknown 1141 public static final int FAILURE_UNKNOWN = 0; 1142 // NONE 1143 public static final int FAILURE_NONE = 1; 1144 // ASSOCIATION_REJECTION_EVENT 1145 public static final int FAILURE_ASSOCIATION_REJECTION = 2; 1146 // AUTHENTICATION_FAILURE_EVENT 1147 public static final int FAILURE_AUTHENTICATION_FAILURE = 3; 1148 // SSID_TEMP_DISABLED (Also Auth failure) 1149 public static final int FAILURE_SSID_TEMP_DISABLED = 4; 1150 // reconnect() or reassociate() call to WifiNative failed 1151 public static final int FAILURE_CONNECT_NETWORK_FAILED = 5; 1152 // NETWORK_DISCONNECTION_EVENT 1153 public static final int FAILURE_NETWORK_DISCONNECTION = 6; 1154 // NEW_CONNECTION_ATTEMPT before previous finished 1155 public static final int FAILURE_NEW_CONNECTION_ATTEMPT = 7; 1156 // New connection attempt to the same network & bssid 1157 public static final int FAILURE_REDUNDANT_CONNECTION_ATTEMPT = 8; 1158 // Roam Watchdog timer triggered (Roaming timed out) 1159 public static final int FAILURE_ROAM_TIMEOUT = 9; 1160 // DHCP failure 1161 public static final int FAILURE_DHCP = 10; 1162 // ASSOCIATION_TIMED_OUT 1163 public static final int FAILURE_ASSOCIATION_TIMED_OUT = 11; 1164 // NETWORK_NOT_FOUND 1165 public static final int FAILURE_NETWORK_NOT_FOUND = 12; 1166 // Connection attempt aborted by the watchdog because the AP didn't respond. 1167 public static final int FAILURE_NO_RESPONSE = 13; 1168 1169 RouterFingerPrint mRouterFingerPrint; 1170 private String mConfigSsid; 1171 private String mConfigBssid; 1172 private int mWifiState; 1173 private boolean mScreenOn; 1174 private int mAuthType; 1175 private int mTrigger; 1176 private boolean mHasEverConnected; 1177 private boolean mIsCarrierWifi; 1178 private boolean mIsOobPseudonymEnabled; 1179 private int mRole; 1180 private int mUid; 1181 private int mCarrierId; 1182 private int mEapType; 1183 private int mPhase2Method; 1184 private int mPasspointRoamingType; 1185 private int mTofuConnectionState; 1186 ConnectionEvent()1187 private ConnectionEvent() { 1188 mConnectionEvent = new WifiMetricsProto.ConnectionEvent(); 1189 mRouterFingerPrint = new RouterFingerPrint(); 1190 mConnectionEvent.routerFingerprint = mRouterFingerPrint.mRouterFingerPrintProto; 1191 mConfigSsid = "<NULL>"; 1192 mConfigBssid = "<NULL>"; 1193 mWifiState = WifiMetricsProto.WifiLog.WIFI_UNKNOWN; 1194 mScreenOn = false; 1195 mIsCarrierWifi = false; 1196 mIsOobPseudonymEnabled = false; 1197 } 1198 toString()1199 public String toString() { 1200 StringBuilder sb = new StringBuilder(); 1201 sb.append("startTime="); 1202 Calendar c = Calendar.getInstance(); 1203 synchronized (mLock) { 1204 c.setTimeInMillis(mConnectionEvent.startTimeMillis); 1205 if (mConnectionEvent.startTimeMillis == 0) { 1206 sb.append(" <null>"); 1207 } else { 1208 sb.append(StringUtil.calendarToString(c)); 1209 } 1210 sb.append(", SSID="); 1211 sb.append(mConfigSsid); 1212 sb.append(", BSSID="); 1213 sb.append(mConfigBssid); 1214 sb.append(", durationMillis="); 1215 sb.append(mConnectionEvent.durationTakenToConnectMillis); 1216 sb.append(", roamType="); 1217 switch(mConnectionEvent.roamType) { 1218 case 1: 1219 sb.append("ROAM_NONE"); 1220 break; 1221 case 2: 1222 sb.append("ROAM_DBDC"); 1223 break; 1224 case 3: 1225 sb.append("ROAM_ENTERPRISE"); 1226 break; 1227 case 4: 1228 sb.append("ROAM_USER_SELECTED"); 1229 break; 1230 case 5: 1231 sb.append("ROAM_UNRELATED"); 1232 break; 1233 default: 1234 sb.append("ROAM_UNKNOWN"); 1235 } 1236 sb.append(", connectionResult="); 1237 sb.append(mConnectionEvent.connectionResult); 1238 sb.append(", level2FailureCode="); 1239 switch(mConnectionEvent.level2FailureCode) { 1240 case FAILURE_NONE: 1241 sb.append("NONE"); 1242 break; 1243 case FAILURE_ASSOCIATION_REJECTION: 1244 sb.append("ASSOCIATION_REJECTION"); 1245 break; 1246 case FAILURE_AUTHENTICATION_FAILURE: 1247 sb.append("AUTHENTICATION_FAILURE"); 1248 break; 1249 case FAILURE_SSID_TEMP_DISABLED: 1250 sb.append("SSID_TEMP_DISABLED"); 1251 break; 1252 case FAILURE_CONNECT_NETWORK_FAILED: 1253 sb.append("CONNECT_NETWORK_FAILED"); 1254 break; 1255 case FAILURE_NETWORK_DISCONNECTION: 1256 sb.append("NETWORK_DISCONNECTION"); 1257 break; 1258 case FAILURE_NEW_CONNECTION_ATTEMPT: 1259 sb.append("NEW_CONNECTION_ATTEMPT"); 1260 break; 1261 case FAILURE_REDUNDANT_CONNECTION_ATTEMPT: 1262 sb.append("REDUNDANT_CONNECTION_ATTEMPT"); 1263 break; 1264 case FAILURE_ROAM_TIMEOUT: 1265 sb.append("ROAM_TIMEOUT"); 1266 break; 1267 case FAILURE_DHCP: 1268 sb.append("DHCP"); 1269 break; 1270 case FAILURE_ASSOCIATION_TIMED_OUT: 1271 sb.append("ASSOCIATION_TIMED_OUT"); 1272 break; 1273 case FAILURE_NETWORK_NOT_FOUND: 1274 sb.append("FAILURE_NETWORK_NOT_FOUND"); 1275 break; 1276 case FAILURE_NO_RESPONSE: 1277 sb.append("FAILURE_NO_RESPONSE"); 1278 break; 1279 default: 1280 sb.append("UNKNOWN"); 1281 break; 1282 } 1283 sb.append(", connectivityLevelFailureCode="); 1284 switch(mConnectionEvent.connectivityLevelFailureCode) { 1285 case WifiMetricsProto.ConnectionEvent.HLF_NONE: 1286 sb.append("NONE"); 1287 break; 1288 case WifiMetricsProto.ConnectionEvent.HLF_DHCP: 1289 sb.append("DHCP"); 1290 break; 1291 case WifiMetricsProto.ConnectionEvent.HLF_NO_INTERNET: 1292 sb.append("NO_INTERNET"); 1293 break; 1294 case WifiMetricsProto.ConnectionEvent.HLF_UNWANTED: 1295 sb.append("UNWANTED"); 1296 break; 1297 default: 1298 sb.append("UNKNOWN"); 1299 break; 1300 } 1301 sb.append(", signalStrength="); 1302 sb.append(mConnectionEvent.signalStrength); 1303 sb.append(", wifiState="); 1304 switch(mWifiState) { 1305 case WifiMetricsProto.WifiLog.WIFI_DISABLED: 1306 sb.append("WIFI_DISABLED"); 1307 break; 1308 case WifiMetricsProto.WifiLog.WIFI_DISCONNECTED: 1309 sb.append("WIFI_DISCONNECTED"); 1310 break; 1311 case WifiMetricsProto.WifiLog.WIFI_ASSOCIATED: 1312 sb.append("WIFI_ASSOCIATED"); 1313 break; 1314 default: 1315 sb.append("WIFI_UNKNOWN"); 1316 break; 1317 } 1318 sb.append(", screenOn="); 1319 sb.append(mScreenOn); 1320 sb.append(", mRouterFingerprint="); 1321 sb.append(mRouterFingerPrint.toString()); 1322 sb.append(", useRandomizedMac="); 1323 sb.append(mConnectionEvent.useRandomizedMac); 1324 sb.append(", useAggressiveMac=" + mConnectionEvent.useAggressiveMac); 1325 sb.append(", connectionNominator="); 1326 switch (mConnectionEvent.connectionNominator) { 1327 case WifiMetricsProto.ConnectionEvent.NOMINATOR_UNKNOWN: 1328 sb.append("NOMINATOR_UNKNOWN"); 1329 break; 1330 case WifiMetricsProto.ConnectionEvent.NOMINATOR_MANUAL: 1331 sb.append("NOMINATOR_MANUAL"); 1332 break; 1333 case WifiMetricsProto.ConnectionEvent.NOMINATOR_SAVED: 1334 sb.append("NOMINATOR_SAVED"); 1335 break; 1336 case WifiMetricsProto.ConnectionEvent.NOMINATOR_SUGGESTION: 1337 sb.append("NOMINATOR_SUGGESTION"); 1338 break; 1339 case WifiMetricsProto.ConnectionEvent.NOMINATOR_PASSPOINT: 1340 sb.append("NOMINATOR_PASSPOINT"); 1341 break; 1342 case WifiMetricsProto.ConnectionEvent.NOMINATOR_CARRIER: 1343 sb.append("NOMINATOR_CARRIER"); 1344 break; 1345 case WifiMetricsProto.ConnectionEvent.NOMINATOR_EXTERNAL_SCORED: 1346 sb.append("NOMINATOR_EXTERNAL_SCORED"); 1347 break; 1348 case WifiMetricsProto.ConnectionEvent.NOMINATOR_SPECIFIER: 1349 sb.append("NOMINATOR_SPECIFIER"); 1350 break; 1351 case WifiMetricsProto.ConnectionEvent.NOMINATOR_SAVED_USER_CONNECT_CHOICE: 1352 sb.append("NOMINATOR_SAVED_USER_CONNECT_CHOICE"); 1353 break; 1354 case WifiMetricsProto.ConnectionEvent.NOMINATOR_OPEN_NETWORK_AVAILABLE: 1355 sb.append("NOMINATOR_OPEN_NETWORK_AVAILABLE"); 1356 break; 1357 default: 1358 sb.append("UnrecognizedNominator(" + mConnectionEvent.connectionNominator 1359 + ")"); 1360 } 1361 sb.append(", networkSelectorExperimentId="); 1362 sb.append(mConnectionEvent.networkSelectorExperimentId); 1363 sb.append(", numBssidInBlocklist=" + mConnectionEvent.numBssidInBlocklist); 1364 sb.append(", level2FailureReason="); 1365 switch(mConnectionEvent.level2FailureReason) { 1366 case WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_NONE: 1367 sb.append("AUTH_FAILURE_NONE"); 1368 break; 1369 case WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_TIMEOUT: 1370 sb.append("AUTH_FAILURE_TIMEOUT"); 1371 break; 1372 case WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_WRONG_PSWD: 1373 sb.append("AUTH_FAILURE_WRONG_PSWD"); 1374 break; 1375 case WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_EAP_FAILURE: 1376 sb.append("AUTH_FAILURE_EAP_FAILURE"); 1377 break; 1378 case WifiMetricsProto.ConnectionEvent.DISCONNECTION_NON_LOCAL: 1379 sb.append("DISCONNECTION_NON_LOCAL"); 1380 break; 1381 default: 1382 sb.append("FAILURE_REASON_UNKNOWN"); 1383 break; 1384 } 1385 sb.append(", networkType="); 1386 switch(mConnectionEvent.networkType) { 1387 case WifiMetricsProto.ConnectionEvent.TYPE_UNKNOWN: 1388 sb.append("TYPE_UNKNOWN"); 1389 break; 1390 case WifiMetricsProto.ConnectionEvent.TYPE_WPA2: 1391 sb.append("TYPE_WPA2"); 1392 break; 1393 case WifiMetricsProto.ConnectionEvent.TYPE_WPA3: 1394 sb.append("TYPE_WPA3"); 1395 break; 1396 case WifiMetricsProto.ConnectionEvent.TYPE_PASSPOINT: 1397 sb.append("TYPE_PASSPOINT"); 1398 break; 1399 case WifiMetricsProto.ConnectionEvent.TYPE_EAP: 1400 sb.append("TYPE_EAP"); 1401 break; 1402 case WifiMetricsProto.ConnectionEvent.TYPE_OWE: 1403 sb.append("TYPE_OWE"); 1404 break; 1405 case WifiMetricsProto.ConnectionEvent.TYPE_OPEN: 1406 sb.append("TYPE_OPEN"); 1407 break; 1408 case WifiMetricsProto.ConnectionEvent.TYPE_WAPI: 1409 sb.append("TYPE_WAPI"); 1410 break; 1411 } 1412 sb.append(", networkCreator="); 1413 switch (mConnectionEvent.networkCreator) { 1414 case WifiMetricsProto.ConnectionEvent.CREATOR_UNKNOWN: 1415 sb.append("CREATOR_UNKNOWN"); 1416 break; 1417 case WifiMetricsProto.ConnectionEvent.CREATOR_USER: 1418 sb.append("CREATOR_USER"); 1419 break; 1420 case WifiMetricsProto.ConnectionEvent.CREATOR_CARRIER: 1421 sb.append("CREATOR_CARRIER"); 1422 break; 1423 } 1424 sb.append(", numConsecutiveConnectionFailure=" 1425 + mConnectionEvent.numConsecutiveConnectionFailure); 1426 sb.append(", isOsuProvisioned=" + mConnectionEvent.isOsuProvisioned); 1427 sb.append(" interfaceName=").append(mConnectionEvent.interfaceName); 1428 sb.append(" interfaceRole=").append( 1429 clientRoleEnumToString(mConnectionEvent.interfaceRole)); 1430 sb.append(", isFirstConnectionAfterBoot=" 1431 + mConnectionEvent.isFirstConnectionAfterBoot); 1432 sb.append(", isCarrierWifi=" + mIsCarrierWifi); 1433 sb.append(", isOobPseudonymEnabled=" + mIsOobPseudonymEnabled); 1434 sb.append(", uid=" + mUid); 1435 return sb.toString(); 1436 } 1437 } 1438 updateFromWifiConfiguration(WifiConfiguration config)1439 private void updateFromWifiConfiguration(WifiConfiguration config) { 1440 synchronized (mLock) { 1441 if (config != null) { 1442 // Is this a hidden network 1443 mRouterFingerPrint.mRouterFingerPrintProto.hidden = config.hiddenSSID; 1444 // Config may not have a valid dtimInterval set yet, in which case dtim will be 1445 // zero (These are only populated from beacon frame scan results, which are 1446 // returned as scan results from the chip far less frequently than 1447 // Probe-responses) 1448 if (config.dtimInterval > 0) { 1449 mRouterFingerPrint.mRouterFingerPrintProto.dtim = config.dtimInterval; 1450 } 1451 1452 if (config.carrierId != TelephonyManager.UNKNOWN_CARRIER_ID) { 1453 mIsCarrierWifi = true; 1454 } 1455 1456 mConfigSsid = config.SSID; 1457 // Get AuthType information from config (We do this again from ScanResult after 1458 // associating with BSSID) 1459 if (config.isSecurityType(WifiConfiguration.SECURITY_TYPE_OPEN)) { 1460 mRouterFingerPrint.mRouterFingerPrintProto.authentication = 1461 WifiMetricsProto.RouterFingerPrint.AUTH_OPEN; 1462 } else if (config.isEnterprise()) { 1463 mRouterFingerPrint.mRouterFingerPrintProto.authentication = 1464 WifiMetricsProto.RouterFingerPrint.AUTH_ENTERPRISE; 1465 } else { 1466 mRouterFingerPrint.mRouterFingerPrintProto.authentication = 1467 WifiMetricsProto.RouterFingerPrint.AUTH_PERSONAL; 1468 } 1469 mRouterFingerPrint.mRouterFingerPrintProto.passpoint = config.isPasspoint(); 1470 mRouterFingerPrint.mRouterFingerPrintProto.isPasspointHomeProvider = 1471 config.isHomeProviderNetwork; 1472 // If there's a ScanResult candidate associated with this config already, get it 1473 // and log (more accurate) metrics from it 1474 ScanResult candidate = config.getNetworkSelectionStatus().getCandidate(); 1475 if (candidate != null) { 1476 updateMetricsFromScanResult(this, candidate); 1477 } 1478 if (mRouterFingerPrint.mRouterFingerPrintProto.authentication 1479 == WifiMetricsProto.RouterFingerPrint.AUTH_ENTERPRISE 1480 && config.enterpriseConfig != null) { 1481 int eapMethod = config.enterpriseConfig.getEapMethod(); 1482 mRouterFingerPrint.mRouterFingerPrintProto.eapMethod = 1483 getEapMethodProto(eapMethod); 1484 int phase2Method = config.enterpriseConfig.getPhase2Method(); 1485 mRouterFingerPrint.mRouterFingerPrintProto.authPhase2Method = 1486 getAuthPhase2MethodProto(phase2Method); 1487 int ocspType = config.enterpriseConfig.getOcsp(); 1488 mRouterFingerPrint.mRouterFingerPrintProto.ocspType = 1489 getOcspTypeProto(ocspType); 1490 } 1491 mTofuConnectionState = convertTofuConnectionStateToProto(config); 1492 } 1493 } 1494 } 1495 } 1496 1497 class WifiOffMetrics { 1498 public int numWifiOff = 0; 1499 public int numWifiOffDeferring = 0; 1500 public int numWifiOffDeferringTimeout = 0; 1501 public final IntCounter wifiOffDeferringTimeHistogram = new IntCounter(); 1502 toProto()1503 public WifiMetricsProto.WifiOffMetrics toProto() { 1504 WifiMetricsProto.WifiOffMetrics proto = 1505 new WifiMetricsProto.WifiOffMetrics(); 1506 proto.numWifiOff = numWifiOff; 1507 proto.numWifiOffDeferring = numWifiOffDeferring; 1508 proto.numWifiOffDeferringTimeout = numWifiOffDeferringTimeout; 1509 proto.wifiOffDeferringTimeHistogram = wifiOffDeferringTimeHistogram.toProto(); 1510 return proto; 1511 } 1512 clear()1513 public void clear() { 1514 numWifiOff = 0; 1515 numWifiOffDeferring = 0; 1516 numWifiOffDeferringTimeout = 0; 1517 wifiOffDeferringTimeHistogram.clear(); 1518 } 1519 1520 @Override toString()1521 public String toString() { 1522 StringBuilder sb = new StringBuilder(); 1523 sb.append("numWifiOff=") 1524 .append(numWifiOff) 1525 .append(", numWifiOffDeferring=") 1526 .append(numWifiOffDeferring) 1527 .append(", numWifiOffDeferringTimeout=") 1528 .append(numWifiOffDeferringTimeout) 1529 .append(", wifiOffDeferringTimeHistogram=") 1530 .append(wifiOffDeferringTimeHistogram); 1531 return sb.toString(); 1532 } 1533 } 1534 1535 class SoftApConfigLimitationMetrics { 1536 // Collect the number of softap security setting reset to default during the restore 1537 public int numSecurityTypeResetToDefault = 0; 1538 // Collect the number of softap max client setting reset to default during the restore 1539 public int numMaxClientSettingResetToDefault = 0; 1540 // Collect the number of softap client control setting reset to default during the restore 1541 public int numClientControlByUserResetToDefault = 0; 1542 // Collect the max client setting when reach it cause client is blocked 1543 public final IntCounter maxClientSettingWhenReachHistogram = new IntCounter(); 1544 toProto()1545 public WifiMetricsProto.SoftApConfigLimitationMetrics toProto() { 1546 WifiMetricsProto.SoftApConfigLimitationMetrics proto = 1547 new WifiMetricsProto.SoftApConfigLimitationMetrics(); 1548 proto.numSecurityTypeResetToDefault = numSecurityTypeResetToDefault; 1549 proto.numMaxClientSettingResetToDefault = numMaxClientSettingResetToDefault; 1550 proto.numClientControlByUserResetToDefault = numClientControlByUserResetToDefault; 1551 proto.maxClientSettingWhenReachHistogram = maxClientSettingWhenReachHistogram.toProto(); 1552 return proto; 1553 } 1554 clear()1555 public void clear() { 1556 numSecurityTypeResetToDefault = 0; 1557 numMaxClientSettingResetToDefault = 0; 1558 numClientControlByUserResetToDefault = 0; 1559 maxClientSettingWhenReachHistogram.clear(); 1560 } 1561 1562 @Override toString()1563 public String toString() { 1564 StringBuilder sb = new StringBuilder(); 1565 sb.append("numSecurityTypeResetToDefault=") 1566 .append(numSecurityTypeResetToDefault) 1567 .append(", numMaxClientSettingResetToDefault=") 1568 .append(numMaxClientSettingResetToDefault) 1569 .append(", numClientControlByUserResetToDefault=") 1570 .append(numClientControlByUserResetToDefault) 1571 .append(", maxClientSettingWhenReachHistogram=") 1572 .append(maxClientSettingWhenReachHistogram); 1573 return sb.toString(); 1574 } 1575 } 1576 1577 class CarrierWifiMetrics { 1578 public int numConnectionSuccess = 0; 1579 public int numConnectionAuthFailure = 0; 1580 public int numConnectionNonAuthFailure = 0; 1581 toProto()1582 public WifiMetricsProto.CarrierWifiMetrics toProto() { 1583 WifiMetricsProto.CarrierWifiMetrics proto = 1584 new WifiMetricsProto.CarrierWifiMetrics(); 1585 proto.numConnectionSuccess = numConnectionSuccess; 1586 proto.numConnectionAuthFailure = numConnectionAuthFailure; 1587 proto.numConnectionNonAuthFailure = numConnectionNonAuthFailure; 1588 return proto; 1589 } 1590 clear()1591 public void clear() { 1592 numConnectionSuccess = 0; 1593 numConnectionAuthFailure = 0; 1594 numConnectionNonAuthFailure = 0; 1595 } 1596 1597 @Override toString()1598 public String toString() { 1599 StringBuilder sb = new StringBuilder(); 1600 sb.append("numConnectionSuccess=") 1601 .append(numConnectionSuccess) 1602 .append(", numConnectionAuthFailure=") 1603 .append(numConnectionAuthFailure) 1604 .append(", numConnectionNonAuthFailure") 1605 .append(numConnectionNonAuthFailure); 1606 return sb.toString(); 1607 } 1608 } 1609 WifiMetrics( Context context, FrameworkFacade facade, Clock clock, Looper looper, WifiAwareMetrics awareMetrics, RttMetrics rttMetrics, WifiPowerMetrics wifiPowerMetrics, WifiP2pMetrics wifiP2pMetrics, DppMetrics dppMetrics, WifiMonitor wifiMonitor, WifiDeviceStateChangeManager wifiDeviceStateChangeManager)1610 public WifiMetrics( 1611 Context context, 1612 FrameworkFacade facade, 1613 Clock clock, 1614 Looper looper, 1615 WifiAwareMetrics awareMetrics, 1616 RttMetrics rttMetrics, 1617 WifiPowerMetrics wifiPowerMetrics, 1618 WifiP2pMetrics wifiP2pMetrics, 1619 DppMetrics dppMetrics, 1620 WifiMonitor wifiMonitor, 1621 WifiDeviceStateChangeManager wifiDeviceStateChangeManager) { 1622 mContext = context; 1623 mFacade = facade; 1624 mClock = clock; 1625 mWifiState = WifiMetricsProto.WifiLog.WIFI_DISABLED; 1626 mRecordStartTimeSec = mClock.getElapsedSinceBootMillis() / 1000; 1627 mWifiAwareMetrics = awareMetrics; 1628 mRttMetrics = rttMetrics; 1629 mWifiPowerMetrics = wifiPowerMetrics; 1630 mWifiP2pMetrics = wifiP2pMetrics; 1631 mDppMetrics = dppMetrics; 1632 mWifiMonitor = wifiMonitor; 1633 mHandler = new Handler(looper) { 1634 public void handleMessage(Message msg) { 1635 synchronized (mLock) { 1636 processMessage(msg); 1637 } 1638 } 1639 }; 1640 1641 mCurrentDeviceMobilityState = WifiManager.DEVICE_MOBILITY_STATE_UNKNOWN; 1642 DeviceMobilityStatePnoScanStats unknownStateStats = 1643 getOrCreateDeviceMobilityStatePnoScanStats(mCurrentDeviceMobilityState); 1644 unknownStateStats.numTimesEnteredState++; 1645 mCurrentDeviceMobilityStateStartMs = mClock.getElapsedSinceBootMillis(); 1646 mCurrentDeviceMobilityStatePnoScanStartMs = -1; 1647 mOnWifiUsabilityListeners = new RemoteCallbackList<>(); 1648 mScanMetrics = new ScanMetrics(context, clock); 1649 wifiDeviceStateChangeManager.registerStateChangeCallback( 1650 new WifiDeviceStateChangeManager.StateChangeCallback() { 1651 @Override 1652 public void onScreenStateChanged(boolean screenOn) { 1653 setScreenState(screenOn); 1654 } 1655 }); 1656 } 1657 1658 /** Sets internal ScoringParams member */ setScoringParams(ScoringParams scoringParams)1659 public void setScoringParams(ScoringParams scoringParams) { 1660 mScoringParams = scoringParams; 1661 } 1662 1663 /** Sets internal WifiConfigManager member */ setWifiConfigManager(WifiConfigManager wifiConfigManager)1664 public void setWifiConfigManager(WifiConfigManager wifiConfigManager) { 1665 mWifiConfigManager = wifiConfigManager; 1666 } 1667 1668 /** Sets internal WifiNetworkSelector member */ setWifiNetworkSelector(WifiNetworkSelector wifiNetworkSelector)1669 public void setWifiNetworkSelector(WifiNetworkSelector wifiNetworkSelector) { 1670 mWifiNetworkSelector = wifiNetworkSelector; 1671 } 1672 1673 /** Sets internal PasspointManager member */ setPasspointManager(PasspointManager passpointManager)1674 public void setPasspointManager(PasspointManager passpointManager) { 1675 mPasspointManager = passpointManager; 1676 } 1677 1678 /** Sets internal WifiDataStall member */ setWifiDataStall(WifiDataStall wifiDataStall)1679 public void setWifiDataStall(WifiDataStall wifiDataStall) { 1680 mWifiDataStall = wifiDataStall; 1681 } 1682 1683 /** Sets internal WifiBlocklistMonitor member */ setWifiBlocklistMonitor(WifiBlocklistMonitor wifiBlocklistMonitor)1684 public void setWifiBlocklistMonitor(WifiBlocklistMonitor wifiBlocklistMonitor) { 1685 mWifiBlocklistMonitor = wifiBlocklistMonitor; 1686 } 1687 1688 /** Sets internal WifiHealthMonitor member */ setWifiHealthMonitor(WifiHealthMonitor wifiHealthMonitor)1689 public void setWifiHealthMonitor(WifiHealthMonitor wifiHealthMonitor) { 1690 mWifiHealthMonitor = wifiHealthMonitor; 1691 } 1692 1693 /** Sets internal WifiScoreCard member */ setWifiScoreCard(WifiScoreCard wifiScoreCard)1694 public void setWifiScoreCard(WifiScoreCard wifiScoreCard) { 1695 mWifiScoreCard = wifiScoreCard; 1696 } 1697 1698 /** Sets internal WifiChannelUtilization member */ setWifiChannelUtilization(WifiChannelUtilization wifiChannelUtilization)1699 public void setWifiChannelUtilization(WifiChannelUtilization wifiChannelUtilization) { 1700 mWifiChannelUtilization = wifiChannelUtilization; 1701 } 1702 1703 /** Sets internal WifiSettingsStore member */ setWifiSettingsStore(WifiSettingsStore wifiSettingsStore)1704 public void setWifiSettingsStore(WifiSettingsStore wifiSettingsStore) { 1705 mWifiSettingsStore = wifiSettingsStore; 1706 } 1707 1708 /** Sets internal ActiveModeWarden member */ setActiveModeWarden(ActiveModeWarden activeModeWarden)1709 public void setActiveModeWarden(ActiveModeWarden activeModeWarden) { 1710 mActiveModeWarden = activeModeWarden; 1711 mActiveModeWarden.registerModeChangeCallback(new ModeChangeCallback()); 1712 } 1713 1714 /** 1715 * Implements callbacks that set the internal ifaceName to ClientRole mapping. 1716 */ 1717 @VisibleForTesting 1718 private class ModeChangeCallback implements ActiveModeWarden.ModeChangeCallback { 1719 @Override onActiveModeManagerAdded(@onNull ActiveModeManager activeModeManager)1720 public void onActiveModeManagerAdded(@NonNull ActiveModeManager activeModeManager) { 1721 if (!(activeModeManager instanceof ConcreteClientModeManager)) { 1722 return; 1723 } 1724 synchronized (mLock) { 1725 ConcreteClientModeManager clientModeManager = 1726 (ConcreteClientModeManager) activeModeManager; 1727 mIfaceToRoleMap.put(clientModeManager.getInterfaceName(), 1728 clientModeManager.getRole()); 1729 } 1730 } 1731 1732 @Override onActiveModeManagerRemoved(@onNull ActiveModeManager activeModeManager)1733 public void onActiveModeManagerRemoved(@NonNull ActiveModeManager activeModeManager) { 1734 if (!(activeModeManager instanceof ConcreteClientModeManager)) { 1735 return; 1736 } 1737 synchronized (mLock) { 1738 ConcreteClientModeManager clientModeManager = 1739 (ConcreteClientModeManager) activeModeManager; 1740 mIfaceToRoleMap.remove(clientModeManager.getInterfaceName()); 1741 } 1742 } 1743 1744 @Override onActiveModeManagerRoleChanged(@onNull ActiveModeManager activeModeManager)1745 public void onActiveModeManagerRoleChanged(@NonNull ActiveModeManager activeModeManager) { 1746 if (!(activeModeManager instanceof ConcreteClientModeManager)) { 1747 return; 1748 } 1749 synchronized (mLock) { 1750 ConcreteClientModeManager clientModeManager = 1751 (ConcreteClientModeManager) activeModeManager; 1752 mIfaceToRoleMap.put(clientModeManager.getInterfaceName(), 1753 clientModeManager.getRole()); 1754 } 1755 } 1756 } 1757 1758 /** 1759 * Increment cumulative counters for link layer stats. 1760 * @param newStats 1761 */ incrementWifiLinkLayerUsageStats(String ifaceName, WifiLinkLayerStats newStats)1762 public void incrementWifiLinkLayerUsageStats(String ifaceName, WifiLinkLayerStats newStats) { 1763 // This is only collected for primary STA currently because RSSI polling is disabled for 1764 // non-primary STAs. 1765 if (!isPrimary(ifaceName)) { 1766 return; 1767 } 1768 if (newStats == null) { 1769 return; 1770 } 1771 if (mLastLinkLayerStats == null) { 1772 mLastLinkLayerStats = newStats; 1773 return; 1774 } 1775 if (!newLinkLayerStatsIsValid(mLastLinkLayerStats, newStats)) { 1776 // This could mean the radio chip is reset or the data is incorrectly reported. 1777 // Don't increment any counts and discard the possibly corrupt |newStats| completely. 1778 mLastLinkLayerStats = null; 1779 return; 1780 } 1781 mWifiLinkLayerUsageStats.loggingDurationMs += 1782 (newStats.timeStampInMs - mLastLinkLayerStats.timeStampInMs); 1783 mWifiLinkLayerUsageStats.radioOnTimeMs += (newStats.on_time - mLastLinkLayerStats.on_time); 1784 mWifiLinkLayerUsageStats.radioTxTimeMs += (newStats.tx_time - mLastLinkLayerStats.tx_time); 1785 mWifiLinkLayerUsageStats.radioRxTimeMs += (newStats.rx_time - mLastLinkLayerStats.rx_time); 1786 mWifiLinkLayerUsageStats.radioScanTimeMs += 1787 (newStats.on_time_scan - mLastLinkLayerStats.on_time_scan); 1788 mWifiLinkLayerUsageStats.radioNanScanTimeMs += 1789 (newStats.on_time_nan_scan - mLastLinkLayerStats.on_time_nan_scan); 1790 mWifiLinkLayerUsageStats.radioBackgroundScanTimeMs += 1791 (newStats.on_time_background_scan - mLastLinkLayerStats.on_time_background_scan); 1792 mWifiLinkLayerUsageStats.radioRoamScanTimeMs += 1793 (newStats.on_time_roam_scan - mLastLinkLayerStats.on_time_roam_scan); 1794 mWifiLinkLayerUsageStats.radioPnoScanTimeMs += 1795 (newStats.on_time_pno_scan - mLastLinkLayerStats.on_time_pno_scan); 1796 mWifiLinkLayerUsageStats.radioHs20ScanTimeMs += 1797 (newStats.on_time_hs20_scan - mLastLinkLayerStats.on_time_hs20_scan); 1798 incrementPerRadioUsageStats(mLastLinkLayerStats, newStats); 1799 1800 mLastLinkLayerStats = newStats; 1801 } 1802 1803 /** 1804 * Increment individual radio stats usage 1805 */ incrementPerRadioUsageStats(WifiLinkLayerStats oldStats, WifiLinkLayerStats newStats)1806 private void incrementPerRadioUsageStats(WifiLinkLayerStats oldStats, 1807 WifiLinkLayerStats newStats) { 1808 if (newStats.radioStats != null && newStats.radioStats.length > 0 1809 && oldStats.radioStats != null && oldStats.radioStats.length > 0 1810 && newStats.radioStats.length == oldStats.radioStats.length) { 1811 int numRadios = newStats.radioStats.length; 1812 for (int i = 0; i < numRadios; i++) { 1813 WifiLinkLayerStats.RadioStat newRadio = newStats.radioStats[i]; 1814 WifiLinkLayerStats.RadioStat oldRadio = oldStats.radioStats[i]; 1815 if (newRadio.radio_id != oldRadio.radio_id) { 1816 continue; 1817 } 1818 RadioStats radioStats = mRadioStats.get(newRadio.radio_id); 1819 if (radioStats == null) { 1820 radioStats = new RadioStats(); 1821 radioStats.radioId = newRadio.radio_id; 1822 mRadioStats.put(newRadio.radio_id, radioStats); 1823 } 1824 radioStats.totalRadioOnTimeMs 1825 += newRadio.on_time - oldRadio.on_time; 1826 radioStats.totalRadioTxTimeMs 1827 += newRadio.tx_time - oldRadio.tx_time; 1828 radioStats.totalRadioRxTimeMs 1829 += newRadio.rx_time - oldRadio.rx_time; 1830 radioStats.totalScanTimeMs 1831 += newRadio.on_time_scan - oldRadio.on_time_scan; 1832 radioStats.totalNanScanTimeMs 1833 += newRadio.on_time_nan_scan - oldRadio.on_time_nan_scan; 1834 radioStats.totalBackgroundScanTimeMs 1835 += newRadio.on_time_background_scan - oldRadio.on_time_background_scan; 1836 radioStats.totalRoamScanTimeMs 1837 += newRadio.on_time_roam_scan - oldRadio.on_time_roam_scan; 1838 radioStats.totalPnoScanTimeMs 1839 += newRadio.on_time_pno_scan - oldRadio.on_time_pno_scan; 1840 radioStats.totalHotspot2ScanTimeMs 1841 += newRadio.on_time_hs20_scan - oldRadio.on_time_hs20_scan; 1842 } 1843 } 1844 } 1845 newLinkLayerStatsIsValid(WifiLinkLayerStats oldStats, WifiLinkLayerStats newStats)1846 private boolean newLinkLayerStatsIsValid(WifiLinkLayerStats oldStats, 1847 WifiLinkLayerStats newStats) { 1848 if (newStats.on_time < oldStats.on_time 1849 || newStats.tx_time < oldStats.tx_time 1850 || newStats.rx_time < oldStats.rx_time 1851 || newStats.on_time_scan < oldStats.on_time_scan) { 1852 return false; 1853 } 1854 return true; 1855 } 1856 1857 /** 1858 * Increment total number of attempts to start a pno scan 1859 */ incrementPnoScanStartAttemptCount()1860 public void incrementPnoScanStartAttemptCount() { 1861 synchronized (mLock) { 1862 mPnoScanMetrics.numPnoScanAttempts++; 1863 } 1864 } 1865 1866 /** 1867 * Increment total number of attempts with pno scan failed 1868 */ incrementPnoScanFailedCount()1869 public void incrementPnoScanFailedCount() { 1870 synchronized (mLock) { 1871 mPnoScanMetrics.numPnoScanFailed++; 1872 } 1873 } 1874 1875 /** 1876 * Increment number of times pno scan found a result 1877 */ incrementPnoFoundNetworkEventCount()1878 public void incrementPnoFoundNetworkEventCount() { 1879 synchronized (mLock) { 1880 mPnoScanMetrics.numPnoFoundNetworkEvents++; 1881 } 1882 } 1883 1884 // Values used for indexing SystemStateEntries 1885 private static final int SCREEN_ON = 1; 1886 private static final int SCREEN_OFF = 0; 1887 convertSecurityTypeToWifiMetricsNetworkType( @ifiConfiguration.SecurityType int type)1888 private int convertSecurityTypeToWifiMetricsNetworkType( 1889 @WifiConfiguration.SecurityType int type) { 1890 switch (type) { 1891 case WifiConfiguration.SECURITY_TYPE_OPEN: 1892 return WifiMetricsProto.ConnectionEvent.TYPE_OPEN; 1893 case WifiConfiguration.SECURITY_TYPE_PSK: 1894 return WifiMetricsProto.ConnectionEvent.TYPE_WPA2; 1895 case WifiConfiguration.SECURITY_TYPE_EAP: 1896 return WifiMetricsProto.ConnectionEvent.TYPE_EAP; 1897 case WifiConfiguration.SECURITY_TYPE_SAE: 1898 return WifiMetricsProto.ConnectionEvent.TYPE_WPA3; 1899 case WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE_192_BIT: 1900 return WifiMetricsProto.ConnectionEvent.TYPE_EAP; 1901 case WifiConfiguration.SECURITY_TYPE_OWE: 1902 return WifiMetricsProto.ConnectionEvent.TYPE_OWE; 1903 case WifiConfiguration.SECURITY_TYPE_WAPI_PSK: 1904 case WifiConfiguration.SECURITY_TYPE_WAPI_CERT: 1905 return WifiMetricsProto.ConnectionEvent.TYPE_WAPI; 1906 case WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE: 1907 return WifiMetricsProto.ConnectionEvent.TYPE_EAP; 1908 // No metric network type for WEP, OSEN, and DPP. 1909 default: 1910 return WifiMetricsProto.ConnectionEvent.TYPE_UNKNOWN; 1911 } 1912 } 1913 1914 /** 1915 * Create a new connection event and check if the new one overlaps with previous one. 1916 * Call when wifi attempts to make a new network connection 1917 * If there is a current 'un-ended' connection event, it will be ended with UNKNOWN connectivity 1918 * failure code. 1919 * Gathers and sets the RouterFingerPrint data as well 1920 * 1921 * @param ifaceName interface name for this connection event 1922 * @param config WifiConfiguration of the config used for the current connection attempt 1923 * @param roamType Roam type that caused connection attempt, see WifiMetricsProto.WifiLog.ROAM_X 1924 * @return The duration in ms since the last unfinished connection attempt, 1925 * or 0 if there is no unfinished connection 1926 */ startConnectionEvent( String ifaceName, WifiConfiguration config, String targetBSSID, int roamType, boolean isOobPseudonymEnabled, int role, int uid)1927 public int startConnectionEvent( 1928 String ifaceName, WifiConfiguration config, String targetBSSID, int roamType, 1929 boolean isOobPseudonymEnabled, int role, int uid) { 1930 synchronized (mLock) { 1931 int overlapWithLastConnectionMs = 0; 1932 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get(ifaceName); 1933 if (currentConnectionEvent != null) { 1934 overlapWithLastConnectionMs = (int) (mClock.getElapsedSinceBootMillis() 1935 - currentConnectionEvent.mConnectionEvent.startTimeSinceBootMillis); 1936 // Is this new Connection Event the same as the current one 1937 if (currentConnectionEvent.mConfigSsid != null 1938 && currentConnectionEvent.mConfigBssid != null 1939 && config != null 1940 && currentConnectionEvent.mConfigSsid.equals(config.SSID) 1941 && (currentConnectionEvent.mConfigBssid.equals("any") 1942 || currentConnectionEvent.mConfigBssid.equals(targetBSSID))) { 1943 currentConnectionEvent.mConfigBssid = targetBSSID; 1944 // End Connection Event due to new connection attempt to the same network 1945 endConnectionEvent(ifaceName, 1946 ConnectionEvent.FAILURE_REDUNDANT_CONNECTION_ATTEMPT, 1947 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1948 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN, 0, 0); 1949 } else { 1950 // End Connection Event due to new connection attempt to different network 1951 endConnectionEvent(ifaceName, 1952 ConnectionEvent.FAILURE_NEW_CONNECTION_ATTEMPT, 1953 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1954 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN, 0, 0); 1955 } 1956 } 1957 // If past maximum connection events, start removing the oldest 1958 while(mConnectionEventList.size() >= MAX_CONNECTION_EVENTS) { 1959 mConnectionEventList.removeFirst(); 1960 } 1961 currentConnectionEvent = new ConnectionEvent(); 1962 mCurrentConnectionEventPerIface.put(ifaceName, currentConnectionEvent); 1963 currentConnectionEvent.mConnectionEvent.interfaceName = ifaceName; 1964 currentConnectionEvent.mConnectionEvent.interfaceRole = convertIfaceToEnum(ifaceName); 1965 currentConnectionEvent.mConnectionEvent.startTimeMillis = 1966 mClock.getWallClockMillis(); 1967 currentConnectionEvent.mConnectionEvent.startTimeSinceBootMillis = 1968 mClock.getElapsedSinceBootMillis(); 1969 currentConnectionEvent.mConfigBssid = targetBSSID; 1970 currentConnectionEvent.mConnectionEvent.roamType = roamType; 1971 currentConnectionEvent.mConnectionEvent.networkSelectorExperimentId = 1972 mNetworkSelectorExperimentId; 1973 currentConnectionEvent.updateFromWifiConfiguration(config); 1974 currentConnectionEvent.mIsOobPseudonymEnabled = isOobPseudonymEnabled; 1975 currentConnectionEvent.mConfigBssid = "any"; 1976 currentConnectionEvent.mWifiState = mWifiState; 1977 currentConnectionEvent.mScreenOn = mScreenOn; 1978 currentConnectionEvent.mConnectionEvent.isFirstConnectionAfterBoot = 1979 mFirstConnectionAfterBoot; 1980 currentConnectionEvent.mRole = role; 1981 currentConnectionEvent.mUid = uid; 1982 mFirstConnectionAfterBoot = false; 1983 mConnectionEventList.add(currentConnectionEvent); 1984 mScanResultRssiTimestampMillis = -1; 1985 if (config != null) { 1986 try { 1987 currentConnectionEvent.mAuthType = config.getAuthType(); 1988 } catch (IllegalStateException e) { 1989 currentConnectionEvent.mAuthType = 0; 1990 } 1991 currentConnectionEvent.mHasEverConnected = 1992 config.getNetworkSelectionStatus().hasEverConnected(); 1993 currentConnectionEvent.mConnectionEvent.useRandomizedMac = 1994 config.macRandomizationSetting 1995 != WifiConfiguration.RANDOMIZATION_NONE; 1996 currentConnectionEvent.mConnectionEvent.useAggressiveMac = 1997 mWifiConfigManager.shouldUseNonPersistentRandomization(config); 1998 currentConnectionEvent.mConnectionEvent.connectionNominator = 1999 mNetworkIdToNominatorId.get(config.networkId, 2000 WifiMetricsProto.ConnectionEvent.NOMINATOR_UNKNOWN); 2001 currentConnectionEvent.mConnectionEvent.isCarrierMerged = config.carrierMerged; 2002 currentConnectionEvent.mCarrierId = config.carrierId; 2003 if (config.enterpriseConfig != null) { 2004 currentConnectionEvent.mEapType = config.enterpriseConfig.getEapMethod(); 2005 currentConnectionEvent.mPhase2Method = 2006 config.enterpriseConfig.getPhase2Method(); 2007 currentConnectionEvent.mPasspointRoamingType = Utils.getRoamingType(config); 2008 } 2009 2010 ScanResult candidate = config.getNetworkSelectionStatus().getCandidate(); 2011 if (candidate != null) { 2012 // Cache the RSSI of the candidate, as the connection event level is updated 2013 // from other sources (polls, bssid_associations) and delta requires the 2014 // scanResult rssi 2015 mScanResultRssi = candidate.level; 2016 mScanResultRssiTimestampMillis = mClock.getElapsedSinceBootMillis(); 2017 } 2018 currentConnectionEvent.mConnectionEvent.numBssidInBlocklist = 2019 mWifiBlocklistMonitor.updateAndGetNumBlockedBssidsForSsid(config.SSID); 2020 currentConnectionEvent.mConnectionEvent.networkType = 2021 WifiMetricsProto.ConnectionEvent.TYPE_UNKNOWN; 2022 currentConnectionEvent.mConnectionEvent.isOsuProvisioned = false; 2023 SecurityParams params = config.getNetworkSelectionStatus() 2024 .getCandidateSecurityParams(); 2025 currentConnectionEvent.mRouterFingerPrint.mSecurityMode = 2026 getSecurityMode(config, true); 2027 if (config.isPasspoint()) { 2028 currentConnectionEvent.mConnectionEvent.networkType = 2029 WifiMetricsProto.ConnectionEvent.TYPE_PASSPOINT; 2030 currentConnectionEvent.mConnectionEvent.isOsuProvisioned = 2031 !TextUtils.isEmpty(config.updateIdentifier); 2032 } else if (null != params) { 2033 currentConnectionEvent.mConnectionEvent.networkType = 2034 convertSecurityTypeToWifiMetricsNetworkType(params.getSecurityType()); 2035 } else if (WifiConfigurationUtil.isConfigForSaeNetwork(config)) { 2036 currentConnectionEvent.mConnectionEvent.networkType = 2037 WifiMetricsProto.ConnectionEvent.TYPE_WPA3; 2038 } else if (WifiConfigurationUtil.isConfigForWapiPskNetwork(config)) { 2039 currentConnectionEvent.mConnectionEvent.networkType = 2040 WifiMetricsProto.ConnectionEvent.TYPE_WAPI; 2041 } else if (WifiConfigurationUtil.isConfigForWapiCertNetwork(config)) { 2042 currentConnectionEvent.mConnectionEvent.networkType = 2043 WifiMetricsProto.ConnectionEvent.TYPE_WAPI; 2044 } else if (WifiConfigurationUtil.isConfigForPskNetwork(config)) { 2045 currentConnectionEvent.mConnectionEvent.networkType = 2046 WifiMetricsProto.ConnectionEvent.TYPE_WPA2; 2047 } else if (WifiConfigurationUtil.isConfigForEnterpriseNetwork(config)) { 2048 currentConnectionEvent.mConnectionEvent.networkType = 2049 WifiMetricsProto.ConnectionEvent.TYPE_EAP; 2050 } else if (WifiConfigurationUtil.isConfigForOweNetwork(config)) { 2051 currentConnectionEvent.mConnectionEvent.networkType = 2052 WifiMetricsProto.ConnectionEvent.TYPE_OWE; 2053 } else if (WifiConfigurationUtil.isConfigForOpenNetwork(config)) { 2054 currentConnectionEvent.mConnectionEvent.networkType = 2055 WifiMetricsProto.ConnectionEvent.TYPE_OPEN; 2056 } 2057 2058 if (!config.fromWifiNetworkSuggestion) { 2059 currentConnectionEvent.mConnectionEvent.networkCreator = 2060 WifiMetricsProto.ConnectionEvent.CREATOR_USER; 2061 } else if (config.carrierId != TelephonyManager.UNKNOWN_CARRIER_ID) { 2062 currentConnectionEvent.mConnectionEvent.networkCreator = 2063 WifiMetricsProto.ConnectionEvent.CREATOR_CARRIER; 2064 } else { 2065 currentConnectionEvent.mConnectionEvent.networkCreator = 2066 WifiMetricsProto.ConnectionEvent.CREATOR_UNKNOWN; 2067 } 2068 2069 currentConnectionEvent.mConnectionEvent.screenOn = mScreenOn; 2070 if (currentConnectionEvent.mConfigSsid != null) { 2071 WifiScoreCard.NetworkConnectionStats recentStats = mWifiScoreCard.lookupNetwork( 2072 currentConnectionEvent.mConfigSsid).getRecentStats(); 2073 currentConnectionEvent.mConnectionEvent.numConsecutiveConnectionFailure = 2074 recentStats.getCount(WifiScoreCard.CNT_CONSECUTIVE_CONNECTION_FAILURE); 2075 } 2076 2077 String ssid = currentConnectionEvent.mConfigSsid; 2078 int nominator = currentConnectionEvent.mConnectionEvent.connectionNominator; 2079 int trigger = WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__TRIGGER__UNKNOWN; 2080 2081 if (nominator == WifiMetricsProto.ConnectionEvent.NOMINATOR_MANUAL) { 2082 trigger = WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__TRIGGER__MANUAL; 2083 } else if (mPreviousSession == null) { 2084 trigger = WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__TRIGGER__AUTOCONNECT_BOOT; 2085 } else if (ssid != null && ssid.equals(mPreviousSession.mSsid)) { 2086 trigger = WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__TRIGGER__RECONNECT_SAME_NETWORK; 2087 } else if (nominator != WifiMetricsProto.ConnectionEvent.NOMINATOR_UNKNOWN) { 2088 trigger = WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__TRIGGER__AUTOCONNECT_CONFIGURED_NETWORK; 2089 } 2090 currentConnectionEvent.mTrigger = trigger; 2091 } 2092 2093 return overlapWithLastConnectionMs; 2094 } 2095 } 2096 2097 /** 2098 * Set AP related metrics from ScanDetail 2099 */ setConnectionScanDetail(String ifaceName, ScanDetail scanDetail)2100 public void setConnectionScanDetail(String ifaceName, ScanDetail scanDetail) { 2101 synchronized (mLock) { 2102 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get(ifaceName); 2103 if (currentConnectionEvent == null || scanDetail == null) { 2104 return; 2105 } 2106 NetworkDetail networkDetail = scanDetail.getNetworkDetail(); 2107 ScanResult scanResult = scanDetail.getScanResult(); 2108 // Ensure that we have a networkDetail, and that it corresponds to the currently 2109 // tracked connection attempt 2110 if (networkDetail == null || scanResult == null 2111 || currentConnectionEvent.mConfigSsid == null 2112 || !currentConnectionEvent.mConfigSsid 2113 .equals("\"" + networkDetail.getSSID() + "\"")) { 2114 return; 2115 } 2116 updateMetricsFromNetworkDetail(currentConnectionEvent, networkDetail); 2117 updateMetricsFromScanResult(currentConnectionEvent, scanResult); 2118 } 2119 } 2120 2121 /** 2122 * Set PMK cache status for a connection event 2123 */ setConnectionPmkCache(String ifaceName, boolean isEnabled)2124 public void setConnectionPmkCache(String ifaceName, boolean isEnabled) { 2125 synchronized (mLock) { 2126 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get(ifaceName); 2127 if (currentConnectionEvent != null) { 2128 currentConnectionEvent.mRouterFingerPrint.setPmkCache(isEnabled); 2129 } 2130 } 2131 } 2132 2133 /** 2134 * Set channel width of the current connection. 2135 */ setConnectionChannelWidth(String interfaceName, @WifiAnnotations.ChannelWidth int channelWidth)2136 public void setConnectionChannelWidth(String interfaceName, 2137 @WifiAnnotations.ChannelWidth int channelWidth) { 2138 synchronized (mLock) { 2139 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get( 2140 interfaceName); 2141 if (currentConnectionEvent != null) { 2142 currentConnectionEvent.mRouterFingerPrint.mChannelWidth = channelWidth; 2143 } 2144 } 2145 } 2146 2147 /** 2148 * Set the max link speed supported by current network 2149 */ setConnectionMaxSupportedLinkSpeedMbps( String ifaceName, int maxSupportedTxLinkSpeedMbps, int maxSupportedRxLinkSpeedMbps)2150 public void setConnectionMaxSupportedLinkSpeedMbps( 2151 String ifaceName, int maxSupportedTxLinkSpeedMbps, int maxSupportedRxLinkSpeedMbps) { 2152 synchronized (mLock) { 2153 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get(ifaceName); 2154 if (currentConnectionEvent != null) { 2155 currentConnectionEvent.mRouterFingerPrint.setMaxSupportedLinkSpeedMbps( 2156 maxSupportedTxLinkSpeedMbps, maxSupportedRxLinkSpeedMbps); 2157 } 2158 } 2159 } 2160 toMetricEapType(int eapType)2161 private int toMetricEapType(int eapType) { 2162 switch (eapType) { 2163 case WifiEnterpriseConfig.Eap.TLS: 2164 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_TLS; 2165 case WifiEnterpriseConfig.Eap.TTLS: 2166 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_TTLS; 2167 case WifiEnterpriseConfig.Eap.SIM: 2168 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_SIM; 2169 case WifiEnterpriseConfig.Eap.AKA: 2170 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_AKA; 2171 case WifiEnterpriseConfig.Eap.AKA_PRIME: 2172 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_AKA_PRIME; 2173 case WifiEnterpriseConfig.Eap.WAPI_CERT: 2174 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_WAPI_CERT; 2175 case WifiEnterpriseConfig.Eap.UNAUTH_TLS: 2176 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_UNAUTH_TLS; 2177 case WifiEnterpriseConfig.Eap.PEAP: 2178 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_PEAP; 2179 case WifiEnterpriseConfig.Eap.PWD: 2180 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_PWD; 2181 default: 2182 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_TYPE__TYPE_EAP_OTHERS; 2183 } 2184 } 2185 toMetricPhase2Method(int phase2Method)2186 private int toMetricPhase2Method(int phase2Method) { 2187 switch (phase2Method) { 2188 case WifiEnterpriseConfig.Phase2.PAP: 2189 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_INNER_METHOD__METHOD_PAP; 2190 case WifiEnterpriseConfig.Phase2.MSCHAP: 2191 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_INNER_METHOD__METHOD_MSCHAP; 2192 case WifiEnterpriseConfig.Phase2.MSCHAPV2: 2193 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_INNER_METHOD__METHOD_MSCHAP_V2; 2194 default: 2195 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__EAP_INNER_METHOD__METHOD_OTHERS; 2196 } 2197 } 2198 2199 /** 2200 * End a Connection event record. Call when wifi connection attempt succeeds or fails. 2201 * If a Connection event has not been started and is active when .end is called, then this 2202 * method will do nothing. 2203 * 2204 * @param ifaceName 2205 * @param level2FailureCode Level 2 failure code returned by supplicant 2206 * @param connectivityFailureCode WifiMetricsProto.ConnectionEvent.HLF_X 2207 * @param level2FailureReason Breakdown of level2FailureCode with more detailed reason 2208 */ endConnectionEvent( String ifaceName, int level2FailureCode, int connectivityFailureCode, int level2FailureReason, int frequency, int statusCode)2209 public void endConnectionEvent( 2210 String ifaceName, 2211 int level2FailureCode, 2212 int connectivityFailureCode, 2213 int level2FailureReason, 2214 int frequency, 2215 int statusCode) { 2216 synchronized (mLock) { 2217 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get(ifaceName); 2218 if (currentConnectionEvent != null) { 2219 boolean connectionSucceeded = (level2FailureCode == 1) 2220 && (connectivityFailureCode == WifiMetricsProto.ConnectionEvent.HLF_NONE); 2221 2222 int band = KnownBandsChannelHelper.getBand(frequency); 2223 int durationTakenToConnectMillis = 2224 (int) (mClock.getElapsedSinceBootMillis() 2225 - currentConnectionEvent.mConnectionEvent.startTimeSinceBootMillis); 2226 2227 if (connectionSucceeded) { 2228 mCurrentSession = new SessionData(currentConnectionEvent, 2229 currentConnectionEvent.mConfigSsid, 2230 mClock.getElapsedSinceBootMillis(), 2231 band, currentConnectionEvent.mAuthType); 2232 if (currentConnectionEvent.mRole == WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__ROLE__ROLE_CLIENT_PRIMARY) { 2233 WifiStatsLog.write(WifiStatsLog.WIFI_CONNECTION_STATE_CHANGED, 2234 true, band, currentConnectionEvent.mAuthType); 2235 } 2236 } 2237 2238 currentConnectionEvent.mConnectionEvent.connectionResult = 2239 connectionSucceeded ? 1 : 0; 2240 currentConnectionEvent.mConnectionEvent.durationTakenToConnectMillis = 2241 durationTakenToConnectMillis; 2242 currentConnectionEvent.mConnectionEvent.level2FailureCode = level2FailureCode; 2243 currentConnectionEvent.mConnectionEvent.connectivityLevelFailureCode = 2244 connectivityFailureCode; 2245 currentConnectionEvent.mConnectionEvent.level2FailureReason = level2FailureReason; 2246 2247 // Write metrics to statsd 2248 int wwFailureCode = getConnectionResultFailureCode(level2FailureCode, 2249 level2FailureReason); 2250 int timeSinceConnectedSeconds = (int) ((mPreviousSession != null 2251 ? (mClock.getElapsedSinceBootMillis() 2252 - mPreviousSession.mSessionEndTimeMillis) : 2253 mClock.getElapsedSinceBootMillis()) / 1000); 2254 WifiStatsLog.write(WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED, 2255 connectionSucceeded, 2256 wwFailureCode, currentConnectionEvent.mConnectionEvent.signalStrength, 2257 durationTakenToConnectMillis, band, currentConnectionEvent.mAuthType, 2258 currentConnectionEvent.mTrigger, 2259 currentConnectionEvent.mHasEverConnected, 2260 timeSinceConnectedSeconds, 2261 currentConnectionEvent.mIsCarrierWifi, 2262 currentConnectionEvent.mIsOobPseudonymEnabled, 2263 currentConnectionEvent.mRole, 2264 statusCode, 2265 toMetricEapType(currentConnectionEvent.mEapType), 2266 toMetricPhase2Method(currentConnectionEvent.mPhase2Method), 2267 currentConnectionEvent.mPasspointRoamingType, 2268 currentConnectionEvent.mCarrierId, 2269 currentConnectionEvent.mTofuConnectionState, 2270 currentConnectionEvent.mUid); 2271 2272 if (connectionSucceeded) { 2273 reportRouterCapabilities(currentConnectionEvent.mRouterFingerPrint); 2274 } 2275 // ConnectionEvent already added to ConnectionEvents List. Safe to remove here. 2276 mCurrentConnectionEventPerIface.remove(ifaceName); 2277 if (!connectionSucceeded) { 2278 mScanResultRssiTimestampMillis = -1; 2279 } 2280 mWifiStatusBuilder.setConnected(connectionSucceeded); 2281 } 2282 } 2283 } 2284 convertTofuConnectionStateToProto(WifiConfiguration config)2285 protected static int convertTofuConnectionStateToProto(WifiConfiguration config) { 2286 if (!config.isEnterprise()) { 2287 return WifiStatsLog 2288 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_CONFIGURATION__TOFU_CONFIGURATION_UNSPECIFIED; 2289 } 2290 2291 switch (config.enterpriseConfig.getTofuConnectionState()) { 2292 case WifiEnterpriseConfig.TOFU_STATE_NOT_ENABLED: 2293 return WifiStatsLog 2294 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_CONFIGURATION__TOFU_CONFIGURATION_NOT_ENABLED; 2295 case WifiEnterpriseConfig.TOFU_STATE_ENABLED_PRE_CONNECTION: 2296 return WifiStatsLog 2297 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_CONFIGURATION__TOFU_CONFIGURATION_ENABLED_PRE_CONNECTION; 2298 case WifiEnterpriseConfig.TOFU_STATE_CONFIGURE_ROOT_CA: 2299 return WifiStatsLog 2300 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_CONFIGURATION__TOFU_CONFIGURATION_CONFIGURE_ROOT_CA; 2301 case WifiEnterpriseConfig.TOFU_STATE_CERT_PINNING: 2302 return WifiStatsLog 2303 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_CONFIGURATION__TOFU_CONFIGURATION_CERT_PINNING; 2304 default: 2305 return WifiStatsLog 2306 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_CONFIGURATION__TOFU_CONFIGURATION_UNSPECIFIED; 2307 } 2308 } 2309 convertTofuDialogStateToProto(WifiConfiguration config)2310 protected static int convertTofuDialogStateToProto(WifiConfiguration config) { 2311 if (!config.isEnterprise()) { 2312 return WifiStatsLog 2313 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_DIALOG_STATE__TOFU_DIALOG_STATE_UNSPECIFIED; 2314 } 2315 2316 switch (config.enterpriseConfig.getTofuDialogState()) { 2317 case WifiEnterpriseConfig.TOFU_DIALOG_STATE_REJECTED: 2318 return WifiStatsLog 2319 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_DIALOG_STATE__TOFU_DIALOG_STATE_REJECTED; 2320 case WifiEnterpriseConfig.TOFU_DIALOG_STATE_ACCEPTED: 2321 return WifiStatsLog 2322 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_DIALOG_STATE__TOFU_DIALOG_STATE_ACCEPTED; 2323 default: 2324 return WifiStatsLog 2325 .WIFI_CONFIGURED_NETWORK_INFO__TOFU_DIALOG_STATE__TOFU_DIALOG_STATE_UNSPECIFIED; 2326 } 2327 } 2328 convertMacRandomizationToProto( @ifiConfiguration.MacRandomizationSetting int macRandomizationSetting)2329 protected static int convertMacRandomizationToProto( 2330 @WifiConfiguration.MacRandomizationSetting int macRandomizationSetting) { 2331 switch (macRandomizationSetting) { 2332 case WifiConfiguration.RANDOMIZATION_NONE: 2333 return WifiStatsLog 2334 .WIFI_CONFIGURED_NETWORK_INFO__MAC_RANDOMIZATION__MAC_RANDOMIZATION_NONE; 2335 case WifiConfiguration.RANDOMIZATION_PERSISTENT: 2336 return WifiStatsLog 2337 .WIFI_CONFIGURED_NETWORK_INFO__MAC_RANDOMIZATION__MAC_RANDOMIZATION_PERSISTENT; 2338 case WifiConfiguration.RANDOMIZATION_NON_PERSISTENT: 2339 return WifiStatsLog 2340 .WIFI_CONFIGURED_NETWORK_INFO__MAC_RANDOMIZATION__MAC_RANDOMIZATION_NON_PERSISTENT; 2341 case WifiConfiguration.RANDOMIZATION_AUTO: 2342 return WifiStatsLog 2343 .WIFI_CONFIGURED_NETWORK_INFO__MAC_RANDOMIZATION__MAC_RANDOMIZATION_AUTO; 2344 default: 2345 return WifiStatsLog 2346 .WIFI_CONFIGURED_NETWORK_INFO__MAC_RANDOMIZATION__MAC_RANDOMIZATION_UNSPECIFIED; 2347 } 2348 } 2349 convertMeteredOverrideToProto( @ifiConfiguration.MeteredOverride int meteredOverride)2350 protected static int convertMeteredOverrideToProto( 2351 @WifiConfiguration.MeteredOverride int meteredOverride) { 2352 switch (meteredOverride) { 2353 case WifiConfiguration.METERED_OVERRIDE_NONE: 2354 return WifiStatsLog 2355 .WIFI_CONFIGURED_NETWORK_INFO__METERED_OVERRIDE__METERED_OVERRIDE_NONE; 2356 case WifiConfiguration.METERED_OVERRIDE_METERED: 2357 return WifiStatsLog 2358 .WIFI_CONFIGURED_NETWORK_INFO__METERED_OVERRIDE__METERED_OVERRIDE_METERED; 2359 case WifiConfiguration.METERED_OVERRIDE_NOT_METERED: 2360 return WifiStatsLog 2361 .WIFI_CONFIGURED_NETWORK_INFO__METERED_OVERRIDE__METERED_OVERRIDE_NOT_METERED; 2362 default: 2363 return WifiStatsLog 2364 .WIFI_CONFIGURED_NETWORK_INFO__METERED_OVERRIDE__METERED_OVERRIDE_UNSPECIFIED; 2365 } 2366 } 2367 getSecurityMode(WifiConfiguration config, boolean useCandidateParams)2368 protected static int getSecurityMode(WifiConfiguration config, boolean useCandidateParams) { 2369 SecurityParams params = 2370 useCandidateParams 2371 ? config.getNetworkSelectionStatus().getCandidateSecurityParams() 2372 : config.getNetworkSelectionStatus().getLastUsedSecurityParams(); 2373 if (params != null) { 2374 return params.getSecurityType(); 2375 } else if (WifiConfigurationUtil.isConfigForWpa3Enterprise192BitNetwork(config)) { 2376 return WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE_192_BIT; 2377 } else if (WifiConfigurationUtil.isConfigForWpa3EnterpriseNetwork(config)) { 2378 return WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE; 2379 } else if (WifiConfigurationUtil.isConfigForDppNetwork(config)) { 2380 return WifiConfiguration.SECURITY_TYPE_DPP; 2381 } else if (WifiConfigurationUtil.isConfigForSaeNetwork(config)) { 2382 return WifiConfiguration.SECURITY_TYPE_SAE; 2383 } else if (WifiConfigurationUtil.isConfigForWapiPskNetwork(config)) { 2384 return WifiConfiguration.SECURITY_TYPE_WAPI_PSK; 2385 } else if (WifiConfigurationUtil.isConfigForWapiCertNetwork(config)) { 2386 return WifiConfiguration.SECURITY_TYPE_WAPI_CERT; 2387 } else if (WifiConfigurationUtil.isConfigForPskNetwork(config)) { 2388 return WifiConfiguration.SECURITY_TYPE_PSK; 2389 } else if (WifiConfigurationUtil.isConfigForOweNetwork(config)) { 2390 return WifiConfiguration.SECURITY_TYPE_OWE; 2391 } else if (WifiConfigurationUtil.isConfigForWepNetwork(config)) { 2392 return WifiConfiguration.SECURITY_TYPE_WEP; 2393 } else if (WifiConfigurationUtil.isConfigForOpenNetwork(config)) { 2394 return WifiConfiguration.SECURITY_TYPE_OPEN; 2395 } else { 2396 Log.e(TAG, "Unknown security mode for config " + config); 2397 return -1; 2398 } 2399 } 2400 2401 /** 2402 * Check if the provided security type is enabled in the security params list. 2403 */ securityTypeEnabled(List<SecurityParams> securityParamsList, int securityType)2404 private static boolean securityTypeEnabled(List<SecurityParams> securityParamsList, 2405 int securityType) { 2406 for (SecurityParams params : securityParamsList) { 2407 if (params.isSecurityType(securityType) && params.isEnabled()) { 2408 return true; 2409 } 2410 } 2411 return false; 2412 } 2413 2414 /** 2415 * Check if any security parameters with the provided type were added by auto-upgrade. 2416 */ securityTypeAddedByAutoUpgrade(List<SecurityParams> securityParamsList, int securityType)2417 private static boolean securityTypeAddedByAutoUpgrade(List<SecurityParams> securityParamsList, 2418 int securityType) { 2419 for (SecurityParams params : securityParamsList) { 2420 if (params.isSecurityType(securityType) && params.isAddedByAutoUpgrade()) { 2421 return true; 2422 } 2423 } 2424 return false; 2425 } 2426 convertSecurityModeToProto(WifiConfiguration config)2427 protected static int convertSecurityModeToProto(WifiConfiguration config) { 2428 if (config == null || config.getDefaultSecurityParams() == null) { 2429 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_UNKNOWN; 2430 } 2431 SecurityParams defaultParams = config.getDefaultSecurityParams(); 2432 List<SecurityParams> securityParamsList = config.getSecurityParamsList(); 2433 switch (defaultParams.getSecurityType()) { 2434 case WifiConfiguration.SECURITY_TYPE_OPEN: 2435 case WifiConfiguration.SECURITY_TYPE_OWE: { 2436 boolean openEnabled = securityTypeEnabled( 2437 securityParamsList, WifiConfiguration.SECURITY_TYPE_OPEN); 2438 boolean oweEnabled = securityTypeEnabled( 2439 securityParamsList, WifiConfiguration.SECURITY_TYPE_OWE); 2440 if (openEnabled && !oweEnabled) { 2441 // OWE params may be disabled or may not exist. 2442 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_NONE; 2443 } else if (!openEnabled && oweEnabled) { 2444 // Open params may get disabled via TDI. 2445 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_OWE; 2446 } 2447 2448 if (securityTypeAddedByAutoUpgrade( 2449 securityParamsList, WifiConfiguration.SECURITY_TYPE_OWE)) { 2450 // User configured this network using Open, but OWE params were auto-added. 2451 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_NONE; 2452 } 2453 // User manually configured this network with both Open and OWE params. 2454 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_OWE_TRANSITION; 2455 } 2456 case WifiConfiguration.SECURITY_TYPE_WEP: 2457 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WEP; 2458 case WifiConfiguration.SECURITY_TYPE_PSK: { 2459 boolean pskEnabled = securityTypeEnabled( 2460 securityParamsList, WifiConfiguration.SECURITY_TYPE_PSK); 2461 boolean saeEnabled = securityTypeEnabled( 2462 securityParamsList, WifiConfiguration.SECURITY_TYPE_SAE); 2463 if (pskEnabled && !saeEnabled) { 2464 // WPA3 params may be disabled or may not exist. 2465 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA2_PERSONAL; 2466 } else if (!pskEnabled && saeEnabled) { 2467 // WPA2 params may get disabled via TDI. 2468 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_PERSONAL; 2469 } 2470 2471 if (securityTypeAddedByAutoUpgrade( 2472 securityParamsList, WifiConfiguration.SECURITY_TYPE_SAE)) { 2473 // User configured this network using WPA2, but WPA3 params were auto-added. 2474 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA2_PERSONAL; 2475 } 2476 // User manually configured this network with both WPA2 and WPA3 params. 2477 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_WPA2_PERSONAL_TRANSITION; 2478 } 2479 case WifiConfiguration.SECURITY_TYPE_SAE: 2480 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_PERSONAL; 2481 case WifiConfiguration.SECURITY_TYPE_WAPI_PSK: 2482 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WAPI_PSK; 2483 case WifiConfiguration.SECURITY_TYPE_WAPI_CERT: 2484 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WAPI_CERT; 2485 case WifiConfiguration.SECURITY_TYPE_DPP: 2486 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_DPP; 2487 case WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE_192_BIT: 2488 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_ENTERPRISE_192_BIT; 2489 case WifiConfiguration.SECURITY_TYPE_EAP: 2490 case WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE: 2491 case WifiConfiguration.SECURITY_TYPE_PASSPOINT_R1_R2: 2492 case WifiConfiguration.SECURITY_TYPE_PASSPOINT_R3: { 2493 if (WifiConfigurationUtil.isConfigForWpa3EnterpriseNetwork(config)) { 2494 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_ENTERPRISE; 2495 } 2496 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA_ENTERPRISE_LEGACY; 2497 } 2498 default: 2499 return WifiStatsLog.WIFI_CONFIGURED_NETWORK_INFO__CONNECTED_SECURITY_MODE__SECURITY_MODE_INVALID; 2500 } 2501 } 2502 convertSecurityModeToProto(@ifiConfiguration.SecurityType int securityMode)2503 static int convertSecurityModeToProto(@WifiConfiguration.SecurityType int securityMode) { 2504 switch (securityMode) { 2505 case WifiConfiguration.SECURITY_TYPE_OPEN: 2506 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_NONE; 2507 case WifiConfiguration.SECURITY_TYPE_WEP: 2508 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WEP; 2509 case WifiConfiguration.SECURITY_TYPE_PSK: 2510 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA2_PERSONAL; 2511 case WifiConfiguration.SECURITY_TYPE_PASSPOINT_R1_R2: 2512 // Passpoint R1 & R2 uses WPA2 Enterprise (Legacy) 2513 case WifiConfiguration.SECURITY_TYPE_EAP: 2514 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA_ENTERPRISE_LEGACY; 2515 case WifiConfiguration.SECURITY_TYPE_SAE: 2516 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_PERSONAL; 2517 case WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE_192_BIT: 2518 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_ENTERPRISE_192_BIT; 2519 case WifiConfiguration.SECURITY_TYPE_OWE: 2520 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_OWE; 2521 case WifiConfiguration.SECURITY_TYPE_WAPI_PSK: 2522 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WAPI_PSK; 2523 case WifiConfiguration.SECURITY_TYPE_WAPI_CERT: 2524 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WAPI_CERT; 2525 case WifiConfiguration.SECURITY_TYPE_PASSPOINT_R3: 2526 // Passpoint R3 uses WPA3 Enterprise 2527 case WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE: 2528 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_WPA3_ENTERPRISE; 2529 case WifiConfiguration.SECURITY_TYPE_DPP: 2530 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_DPP; 2531 default: 2532 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CONNECTED_SECURITY_MODE__SECURITY_MODE_UNKNOWN; 2533 } 2534 } 2535 convertHsReleasetoProto(NetworkDetail.HSRelease hsRelease)2536 private int convertHsReleasetoProto(NetworkDetail.HSRelease hsRelease) { 2537 if (hsRelease == NetworkDetail.HSRelease.R1) { 2538 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__PASSPOINT_RELEASE__PASSPOINT_RELEASE_1; 2539 } else if (hsRelease == NetworkDetail.HSRelease.R2) { 2540 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__PASSPOINT_RELEASE__PASSPOINT_RELEASE_2; 2541 } else if (hsRelease == NetworkDetail.HSRelease.R3) { 2542 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__PASSPOINT_RELEASE__PASSPOINT_RELEASE_3; 2543 } else { 2544 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__PASSPOINT_RELEASE__PASSPOINT_RELEASE_UNKNOWN; 2545 } 2546 } 2547 convertApType6GhzToProto(ApType6GHz apType6Ghz)2548 private int convertApType6GhzToProto(ApType6GHz apType6Ghz) { 2549 if (apType6Ghz == ApType6GHz.AP_TYPE_6GHZ_INDOOR) { 2550 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__AP_TYPE_6GHZ__AP_TYPE_6GHZ_INDOOR; 2551 } else if (apType6Ghz == ApType6GHz.AP_TYPE_6GHZ_STANDARD_POWER) { 2552 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__AP_TYPE_6GHZ__AP_TYPE_6GHZ_STANDARD_POWER; 2553 } else { 2554 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__AP_TYPE_6GHZ__AP_TYPE_6HZ_UNKNOWN; 2555 } 2556 } 2557 convertWifiStandardToProto(int wifiMode)2558 private int convertWifiStandardToProto(int wifiMode) { 2559 switch (wifiMode) { 2560 case WifiMode.MODE_11A: 2561 case WifiMode.MODE_11B: 2562 case WifiMode.MODE_11G: 2563 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__STANDARD__WIFI_STANDARD_LEGACY; 2564 case WifiMode.MODE_11N: 2565 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__STANDARD__WIFI_STANDARD_11N; 2566 case WifiMode.MODE_11AC: 2567 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__STANDARD__WIFI_STANDARD_11AC; 2568 case WifiMode.MODE_11AX: 2569 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__STANDARD__WIFI_STANDARD_11AX; 2570 case WifiMode.MODE_11BE: 2571 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__STANDARD__WIFI_STANDARD_11BE; 2572 case WifiMode.MODE_UNDEFINED: 2573 default: 2574 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__STANDARD__WIFI_STANDARD_UNKNOWN; 2575 } 2576 2577 } 2578 convertEapMethodToProto(WifiConfiguration config)2579 protected static int convertEapMethodToProto(WifiConfiguration config) { 2580 if (config.enterpriseConfig == null) { 2581 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_UNKNOWN; 2582 } 2583 return convertEapMethodToProto(config.enterpriseConfig.getEapMethod()); 2584 } 2585 convertEapMethodToProto(int eapMethod)2586 private static int convertEapMethodToProto(int eapMethod) { 2587 switch (eapMethod) { 2588 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_WAPI_CERT: 2589 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_WAPI_CERT; 2590 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_TLS: 2591 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_TLS; 2592 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_UNAUTH_TLS: 2593 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_UNAUTH_TLS; 2594 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_PEAP: 2595 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_PEAP; 2596 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_PWD: 2597 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_PWD; 2598 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_TTLS: 2599 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_TTLS; 2600 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_SIM: 2601 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_SIM; 2602 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_AKA: 2603 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_AKA; 2604 case WifiMetricsProto.RouterFingerPrint.TYPE_EAP_AKA_PRIME: 2605 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_EAP_AKA_PRIME; 2606 default: 2607 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_TYPE__TYPE_UNKNOWN; 2608 } 2609 } 2610 convertEapInnerMethodToProto(WifiConfiguration config)2611 protected static int convertEapInnerMethodToProto(WifiConfiguration config) { 2612 if (config.enterpriseConfig == null) { 2613 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_UNKNOWN; 2614 } 2615 int phase2Method = config.enterpriseConfig.getPhase2Method(); 2616 return convertEapInnerMethodToProto(getAuthPhase2MethodProto(phase2Method)); 2617 } 2618 convertEapInnerMethodToProto(int phase2Method)2619 private static int convertEapInnerMethodToProto(int phase2Method) { 2620 switch (phase2Method) { 2621 case WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_PAP: 2622 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_PAP; 2623 case WifiEnterpriseConfig.Phase2.MSCHAP: 2624 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_MSCHAP; 2625 case WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_MSCHAPV2: 2626 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_MSCHAP_V2; 2627 case WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_GTC: 2628 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_GTC; 2629 case WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_SIM: 2630 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_SIM; 2631 case WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_AKA: 2632 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_AKA; 2633 case WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_AKA_PRIME: 2634 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_AKA_PRIME; 2635 default: 2636 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__EAP_INNER_METHOD__METHOD_UNKNOWN; 2637 } 2638 } 2639 convertOcspTypeToProto(int ocspType)2640 private int convertOcspTypeToProto(int ocspType) { 2641 switch (ocspType) { 2642 case WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_NONE: 2643 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__OCSP_TYPE__TYPE_OCSP_NONE; 2644 case WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_REQUEST_CERT_STATUS: 2645 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__OCSP_TYPE__TYPE_OCSP_REQUEST_CERT_STATUS; 2646 case WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_REQUIRE_CERT_STATUS: 2647 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__OCSP_TYPE__TYPE_OCSP_REQUIRE_CERT_STATUS; 2648 case WifiMetricsProto.RouterFingerPrint.TYPE_OCSP_REQUIRE_ALL_NON_TRUSTED_CERTS_STATUS: 2649 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__OCSP_TYPE__TYPE_OCSP_REQUIRE_ALL_NON_TRUSTED_CERTS_STATUS; 2650 default: 2651 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__OCSP_TYPE__TYPE_OCSP_UNKNOWN; 2652 } 2653 } 2654 isFreeOpenRoaming(WifiConfiguration config)2655 protected static boolean isFreeOpenRoaming(WifiConfiguration config) { 2656 return Utils.getRoamingType(config) 2657 == WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__PASSPOINT_ROAMING_TYPE__ROAMING_RCOI_OPENROAMING_FREE; 2658 } 2659 isSettledOpenRoaming(WifiConfiguration config)2660 protected static boolean isSettledOpenRoaming(WifiConfiguration config) { 2661 return Utils.getRoamingType(config) 2662 == WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__PASSPOINT_ROAMING_TYPE__ROAMING_RCOI_OPENROAMING_SETTLED; 2663 } 2664 convertChannelWidthToProto(@ifiAnnotations.ChannelWidth int channelWidth)2665 private int convertChannelWidthToProto(@WifiAnnotations.ChannelWidth int channelWidth) { 2666 switch(channelWidth) { 2667 case ScanResult.CHANNEL_WIDTH_20MHZ: 2668 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_20MHZ; 2669 case ScanResult.CHANNEL_WIDTH_40MHZ: 2670 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_40MHZ; 2671 case ScanResult.CHANNEL_WIDTH_80MHZ: 2672 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_80MHZ; 2673 case ScanResult.CHANNEL_WIDTH_160MHZ: 2674 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_160MHZ; 2675 case ScanResult.CHANNEL_WIDTH_80MHZ_PLUS_MHZ: 2676 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_80MHZ_PLUS_MHZ; 2677 case ScanResult.CHANNEL_WIDTH_320MHZ: 2678 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_320MHZ; 2679 default: 2680 return WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED__CHANNEL_WIDTH_MHZ__CHANNEL_WIDTH_UNKNOWN; 2681 } 2682 } 2683 reportRouterCapabilities(RouterFingerPrint r)2684 private void reportRouterCapabilities(RouterFingerPrint r) { 2685 WifiStatsLog.write(WifiStatsLog.WIFI_AP_CAPABILITIES_REPORTED, 2686 r.mIsFrameworkInitiatedRoaming, r.mRouterFingerPrintProto.channelInfo, 2687 KnownBandsChannelHelper.getBand(r.mRouterFingerPrintProto.channelInfo), 2688 r.mRouterFingerPrintProto.dtim, convertSecurityModeToProto(r.mSecurityMode), 2689 r.mRouterFingerPrintProto.hidden, r.mIsIncorrectlyConfiguredAsHidden, 2690 convertWifiStandardToProto(r.mWifiStandard), r.mIs11bSupported, 2691 convertEapMethodToProto(r.mRouterFingerPrintProto.eapMethod), 2692 convertEapInnerMethodToProto(r.mRouterFingerPrintProto.authPhase2Method), 2693 convertOcspTypeToProto(r.mRouterFingerPrintProto.ocspType), 2694 r.mRouterFingerPrintProto.pmkCacheEnabled, r.mIsMboSupported, r.mIsOceSupported, 2695 r.mIsFilsSupported, r.mIsTwtRequired, r.mIsIndividualTwtSupported, 2696 r.mIsBroadcastTwtSupported, r.mIsRestrictedTwtSupported, r.mIs11McSupported, 2697 r.mIs11AzSupported, convertHsReleasetoProto(r.mHsRelease), 2698 r.mRouterFingerPrintProto.isPasspointHomeProvider, 2699 convertApType6GhzToProto(r.mApType6GHz), r.mIsEcpsPriorityAccessSupported, 2700 convertChannelWidthToProto(r.mChannelWidth)); 2701 } 2702 2703 /** 2704 * Report that an active Wifi network connection was dropped. 2705 * 2706 * @param disconnectReason Error code for the disconnect. 2707 * @param rssi Last seen RSSI. 2708 * @param linkSpeed Last seen link speed. 2709 */ reportNetworkDisconnect(String ifaceName, int disconnectReason, int rssi, int linkSpeed, long lastRssiUpdateMillis)2710 public void reportNetworkDisconnect(String ifaceName, int disconnectReason, int rssi, 2711 int linkSpeed, long lastRssiUpdateMillis) { 2712 synchronized (mLock) { 2713 if (!isPrimary(ifaceName)) { 2714 return; 2715 } 2716 if (mCurrentSession != null) { 2717 if (mCurrentSession.mConnectionEvent.mRole == WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__ROLE__ROLE_CLIENT_PRIMARY) { 2718 WifiStatsLog.write(WifiStatsLog.WIFI_CONNECTION_STATE_CHANGED, 2719 false, 2720 mCurrentSession.mBand, 2721 mCurrentSession.mAuthType); 2722 } 2723 mCurrentSession.mSessionEndTimeMillis = mClock.getElapsedSinceBootMillis(); 2724 int durationSeconds = (int) (mCurrentSession.mSessionEndTimeMillis 2725 - mCurrentSession.mSessionStartTimeMillis) / 1000; 2726 int connectedSinceLastRoamSeconds = (int) (mCurrentSession.mSessionEndTimeMillis 2727 - mCurrentSession.mLastRoamCompleteMillis) / 1000; 2728 int timeSinceLastRssiUpdateSeconds = (int) (mClock.getElapsedSinceBootMillis() 2729 - lastRssiUpdateMillis) / 1000; 2730 2731 WifiStatsLog.write(WifiStatsLog.WIFI_DISCONNECT_REPORTED, 2732 durationSeconds, 2733 disconnectReason, 2734 mCurrentSession.mBand, 2735 mCurrentSession.mAuthType, 2736 rssi, 2737 linkSpeed, 2738 timeSinceLastRssiUpdateSeconds, 2739 connectedSinceLastRoamSeconds, 2740 mCurrentSession.mConnectionEvent.mRole, 2741 toMetricEapType(mCurrentSession.mConnectionEvent.mEapType), 2742 toMetricPhase2Method(mCurrentSession.mConnectionEvent.mPhase2Method), 2743 mCurrentSession.mConnectionEvent.mPasspointRoamingType, 2744 mCurrentSession.mConnectionEvent.mCarrierId, 2745 mCurrentSession.mConnectionEvent.mUid); 2746 2747 mPreviousSession = mCurrentSession; 2748 mCurrentSession = null; 2749 } 2750 } 2751 } 2752 2753 /** 2754 * Report an airplane mode session. 2755 * 2756 * @param wifiOnBeforeEnteringApm Whether Wi-Fi is on before entering airplane mode 2757 * @param wifiOnAfterEnteringApm Whether Wi-Fi is on after entering airplane mode 2758 * @param wifiOnBeforeExitingApm Whether Wi-Fi is on before exiting airplane mode 2759 * @param apmEnhancementActive Whether the user has activated the airplane mode enhancement 2760 * feature by toggling Wi-Fi in airplane mode 2761 * @param userToggledWifiDuringApm Whether the user toggled Wi-Fi during the current 2762 * airplane mode 2763 * @param userToggledWifiAfterEnteringApmWithinMinute Whether the user toggled Wi-Fi within one 2764 * minute of entering airplane mode 2765 */ reportAirplaneModeSession(boolean wifiOnBeforeEnteringApm, boolean wifiOnAfterEnteringApm, boolean wifiOnBeforeExitingApm, boolean apmEnhancementActive, boolean userToggledWifiDuringApm, boolean userToggledWifiAfterEnteringApmWithinMinute)2766 public void reportAirplaneModeSession(boolean wifiOnBeforeEnteringApm, 2767 boolean wifiOnAfterEnteringApm, boolean wifiOnBeforeExitingApm, 2768 boolean apmEnhancementActive, boolean userToggledWifiDuringApm, 2769 boolean userToggledWifiAfterEnteringApmWithinMinute) { 2770 WifiStatsLog.write(WifiStatsLog.AIRPLANE_MODE_SESSION_REPORTED, 2771 WifiStatsLog.AIRPLANE_MODE_SESSION_REPORTED__PACKAGE_NAME__WIFI, 2772 wifiOnBeforeEnteringApm, wifiOnAfterEnteringApm, wifiOnBeforeExitingApm, 2773 apmEnhancementActive, userToggledWifiDuringApm, 2774 userToggledWifiAfterEnteringApmWithinMinute, false); 2775 } 2776 2777 /** 2778 * Report a Wi-Fi state change. 2779 * 2780 * @param wifiState Whether Wi-Fi is enabled 2781 * @param wifiWakeState Whether Wi-Fi Wake is enabled 2782 * @param enabledByWifiWake Whether Wi-Fi was enabled by Wi-Fi Wake 2783 */ reportWifiStateChanged(boolean wifiState, boolean wifiWakeState, boolean enabledByWifiWake)2784 public void reportWifiStateChanged(boolean wifiState, boolean wifiWakeState, 2785 boolean enabledByWifiWake) { 2786 WifiStatsLog.write(WifiStatsLog.WIFI_STATE_CHANGED, wifiState, wifiWakeState, 2787 enabledByWifiWake); 2788 } 2789 getConnectionResultFailureCode(int level2FailureCode, int level2FailureReason)2790 private int getConnectionResultFailureCode(int level2FailureCode, int level2FailureReason) { 2791 switch (level2FailureCode) { 2792 case ConnectionEvent.FAILURE_NONE: 2793 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_UNKNOWN; 2794 case ConnectionEvent.FAILURE_ASSOCIATION_TIMED_OUT: 2795 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_ASSOCIATION_TIMEOUT; 2796 case ConnectionEvent.FAILURE_ASSOCIATION_REJECTION: 2797 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_ASSOCIATION_REJECTION; 2798 case ConnectionEvent.FAILURE_AUTHENTICATION_FAILURE: 2799 switch (level2FailureReason) { 2800 case WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_EAP_FAILURE: 2801 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_AUTHENTICATION_EAP; 2802 case WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_WRONG_PSWD: 2803 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_WRONG_PASSWORD; 2804 default: 2805 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_AUTHENTICATION_GENERAL; 2806 } 2807 case ConnectionEvent.FAILURE_DHCP: 2808 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_DHCP; 2809 case ConnectionEvent.FAILURE_NETWORK_DISCONNECTION: 2810 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_NETWORK_DISCONNECTION; 2811 case ConnectionEvent.FAILURE_ROAM_TIMEOUT: 2812 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_ROAM_TIMEOUT; 2813 case ConnectionEvent.FAILURE_CONNECT_NETWORK_FAILED: 2814 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_CONNECT_NETWORK_FAILED; 2815 case ConnectionEvent.FAILURE_NEW_CONNECTION_ATTEMPT: 2816 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_NEW_CONNECTION_ATTEMPT; 2817 case ConnectionEvent.FAILURE_REDUNDANT_CONNECTION_ATTEMPT: 2818 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_REDUNDANT_CONNECTION_ATTEMPT; 2819 case ConnectionEvent.FAILURE_NETWORK_NOT_FOUND: 2820 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_NETWORK_NOT_FOUND; 2821 case ConnectionEvent.FAILURE_NO_RESPONSE: 2822 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_NO_RESPONSE; 2823 default: 2824 return WifiStatsLog.WIFI_CONNECTION_RESULT_REPORTED__FAILURE_CODE__FAILURE_OTHERS; 2825 } 2826 } 2827 2828 /** 2829 * Set ConnectionEvent DTIM Interval (if set), and 802.11 Connection mode, from NetworkDetail 2830 */ updateMetricsFromNetworkDetail( ConnectionEvent currentConnectionEvent, NetworkDetail networkDetail)2831 private void updateMetricsFromNetworkDetail( 2832 ConnectionEvent currentConnectionEvent, NetworkDetail networkDetail) { 2833 int dtimInterval = networkDetail.getDtimInterval(); 2834 if (dtimInterval > 0) { 2835 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.dtim = 2836 dtimInterval; 2837 } 2838 2839 if (currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.hidden 2840 && !networkDetail.isHiddenBeaconFrame()) { 2841 currentConnectionEvent.mRouterFingerPrint.mIsIncorrectlyConfiguredAsHidden = true; 2842 } 2843 2844 final int connectionWifiMode; 2845 switch (networkDetail.getWifiMode()) { 2846 case InformationElementUtil.WifiMode.MODE_UNDEFINED: 2847 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_UNKNOWN; 2848 break; 2849 case InformationElementUtil.WifiMode.MODE_11A: 2850 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_A; 2851 break; 2852 case InformationElementUtil.WifiMode.MODE_11B: 2853 currentConnectionEvent.mRouterFingerPrint.mIs11bSupported = true; 2854 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_B; 2855 break; 2856 case InformationElementUtil.WifiMode.MODE_11G: 2857 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_G; 2858 break; 2859 case InformationElementUtil.WifiMode.MODE_11N: 2860 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_N; 2861 break; 2862 case InformationElementUtil.WifiMode.MODE_11AC : 2863 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_AC; 2864 break; 2865 case InformationElementUtil.WifiMode.MODE_11AX : 2866 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_AX; 2867 break; 2868 default: 2869 connectionWifiMode = WifiMetricsProto.RouterFingerPrint.ROUTER_TECH_OTHER; 2870 break; 2871 } 2872 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.routerTechnology = 2873 connectionWifiMode; 2874 currentConnectionEvent.mRouterFingerPrint.mWifiStandard = networkDetail.getWifiMode(); 2875 2876 if (networkDetail.isMboSupported()) { 2877 mWifiLogProto.numConnectToNetworkSupportingMbo++; 2878 if (networkDetail.isOceSupported()) { 2879 mWifiLogProto.numConnectToNetworkSupportingOce++; 2880 } 2881 } 2882 2883 currentConnectionEvent.mRouterFingerPrint.mApType6GHz = 2884 networkDetail.getApType6GHz(); 2885 currentConnectionEvent.mRouterFingerPrint.mIsBroadcastTwtSupported = 2886 networkDetail.isBroadcastTwtSupported(); 2887 currentConnectionEvent.mRouterFingerPrint.mIsRestrictedTwtSupported = 2888 networkDetail.isRestrictedTwtSupported(); 2889 currentConnectionEvent.mRouterFingerPrint.mIsIndividualTwtSupported = 2890 networkDetail.isIndividualTwtSupported(); 2891 currentConnectionEvent.mRouterFingerPrint.mIsTwtRequired = networkDetail.isTwtRequired(); 2892 currentConnectionEvent.mRouterFingerPrint.mIsFilsSupported = networkDetail.isFilsCapable(); 2893 currentConnectionEvent.mRouterFingerPrint.mIs11AzSupported = 2894 networkDetail.is80211azNtbResponder() || networkDetail.is80211azTbResponder(); 2895 currentConnectionEvent.mRouterFingerPrint.mIs11McSupported = 2896 networkDetail.is80211McResponderSupport(); 2897 currentConnectionEvent.mRouterFingerPrint.mIsMboSupported = networkDetail.isMboSupported(); 2898 currentConnectionEvent.mRouterFingerPrint.mIsOceSupported = networkDetail.isOceSupported(); 2899 currentConnectionEvent.mRouterFingerPrint.mIsEcpsPriorityAccessSupported = 2900 networkDetail.isEpcsPriorityAccessSupported(); 2901 currentConnectionEvent.mRouterFingerPrint.mHsRelease = networkDetail.getHSRelease(); 2902 } 2903 2904 /** 2905 * Set ConnectionEvent RSSI and authentication type from ScanResult 2906 */ updateMetricsFromScanResult( ConnectionEvent currentConnectionEvent, ScanResult scanResult)2907 private void updateMetricsFromScanResult( 2908 ConnectionEvent currentConnectionEvent, ScanResult scanResult) { 2909 currentConnectionEvent.mConnectionEvent.signalStrength = scanResult.level; 2910 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.authentication = 2911 WifiMetricsProto.RouterFingerPrint.AUTH_OPEN; 2912 currentConnectionEvent.mConfigBssid = scanResult.BSSID; 2913 if (scanResult.capabilities != null) { 2914 if (ScanResultUtil.isScanResultForWepNetwork(scanResult)) { 2915 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.authentication = 2916 WifiMetricsProto.RouterFingerPrint.AUTH_PERSONAL; 2917 } else if (ScanResultUtil.isScanResultForPskNetwork(scanResult) 2918 || ScanResultUtil.isScanResultForSaeNetwork(scanResult)) { 2919 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.authentication = 2920 WifiMetricsProto.RouterFingerPrint.AUTH_PERSONAL; 2921 } else if (ScanResultUtil.isScanResultForWpa3EnterpriseTransitionNetwork(scanResult) 2922 || ScanResultUtil.isScanResultForWpa3EnterpriseOnlyNetwork(scanResult) 2923 || ScanResultUtil.isScanResultForWpa2EnterpriseOnlyNetwork(scanResult) 2924 || ScanResultUtil.isScanResultForEapSuiteBNetwork(scanResult)) { 2925 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.authentication = 2926 WifiMetricsProto.RouterFingerPrint.AUTH_ENTERPRISE; 2927 } 2928 } 2929 currentConnectionEvent.mRouterFingerPrint.mRouterFingerPrintProto.channelInfo = 2930 scanResult.frequency; 2931 } 2932 setIsLocationEnabled(boolean enabled)2933 void setIsLocationEnabled(boolean enabled) { 2934 synchronized (mLock) { 2935 mWifiLogProto.isLocationEnabled = enabled; 2936 } 2937 } 2938 setIsScanningAlwaysEnabled(boolean enabled)2939 void setIsScanningAlwaysEnabled(boolean enabled) { 2940 synchronized (mLock) { 2941 mWifiLogProto.isScanningAlwaysEnabled = enabled; 2942 } 2943 } 2944 2945 /** 2946 * Developer options toggle value for verbose logging. 2947 */ setVerboseLoggingEnabled(boolean enabled)2948 public void setVerboseLoggingEnabled(boolean enabled) { 2949 synchronized (mLock) { 2950 mWifiLogProto.isVerboseLoggingEnabled = enabled; 2951 } 2952 } 2953 2954 /** 2955 * Developer options toggle value for non-persistent MAC randomization. 2956 */ setNonPersistentMacRandomizationForceEnabled(boolean enabled)2957 public void setNonPersistentMacRandomizationForceEnabled(boolean enabled) { 2958 synchronized (mLock) { 2959 mWifiLogProto.isEnhancedMacRandomizationForceEnabled = enabled; 2960 } 2961 } 2962 2963 /** 2964 * Wifi wake feature toggle. 2965 */ setWifiWakeEnabled(boolean enabled)2966 public void setWifiWakeEnabled(boolean enabled) { 2967 synchronized (mLock) { 2968 mWifiLogProto.isWifiWakeEnabled = enabled; 2969 } 2970 } 2971 2972 /** 2973 * Increment Non Empty Scan Results count 2974 */ incrementNonEmptyScanResultCount()2975 public void incrementNonEmptyScanResultCount() { 2976 if (DBG) Log.v(TAG, "incrementNonEmptyScanResultCount"); 2977 synchronized (mLock) { 2978 mWifiLogProto.numNonEmptyScanResults++; 2979 } 2980 } 2981 2982 /** 2983 * Increment Empty Scan Results count 2984 */ incrementEmptyScanResultCount()2985 public void incrementEmptyScanResultCount() { 2986 if (DBG) Log.v(TAG, "incrementEmptyScanResultCount"); 2987 synchronized (mLock) { 2988 mWifiLogProto.numEmptyScanResults++; 2989 } 2990 } 2991 2992 /** 2993 * Increment background scan count 2994 */ incrementBackgroundScanCount()2995 public void incrementBackgroundScanCount() { 2996 if (DBG) Log.v(TAG, "incrementBackgroundScanCount"); 2997 synchronized (mLock) { 2998 mWifiLogProto.numBackgroundScans++; 2999 } 3000 } 3001 3002 /** 3003 * Get Background scan count 3004 */ getBackgroundScanCount()3005 public int getBackgroundScanCount() { 3006 synchronized (mLock) { 3007 return mWifiLogProto.numBackgroundScans; 3008 } 3009 } 3010 3011 /** 3012 * Increment oneshot scan count, and the associated WifiSystemScanStateCount entry 3013 */ incrementOneshotScanCount()3014 public void incrementOneshotScanCount() { 3015 synchronized (mLock) { 3016 mWifiLogProto.numOneshotScans++; 3017 } 3018 incrementWifiSystemScanStateCount(mWifiState, mScreenOn); 3019 } 3020 3021 /** 3022 * Increment the count of oneshot scans that include DFS channels. 3023 */ incrementOneshotScanWithDfsCount()3024 public void incrementOneshotScanWithDfsCount() { 3025 synchronized (mLock) { 3026 mWifiLogProto.numOneshotHasDfsChannelScans++; 3027 } 3028 } 3029 3030 /** 3031 * Increment connectivity oneshot scan count. 3032 */ incrementConnectivityOneshotScanCount()3033 public void incrementConnectivityOneshotScanCount() { 3034 synchronized (mLock) { 3035 mWifiLogProto.numConnectivityOneshotScans++; 3036 } 3037 } 3038 3039 /** 3040 * Get oneshot scan count 3041 */ getOneshotScanCount()3042 public int getOneshotScanCount() { 3043 synchronized (mLock) { 3044 return mWifiLogProto.numOneshotScans; 3045 } 3046 } 3047 3048 /** 3049 * Get connectivity oneshot scan count 3050 */ getConnectivityOneshotScanCount()3051 public int getConnectivityOneshotScanCount() { 3052 synchronized (mLock) { 3053 return mWifiLogProto.numConnectivityOneshotScans; 3054 } 3055 } 3056 3057 /** 3058 * Get the count of oneshot scan requests that included DFS channels. 3059 */ getOneshotScanWithDfsCount()3060 public int getOneshotScanWithDfsCount() { 3061 synchronized (mLock) { 3062 return mWifiLogProto.numOneshotHasDfsChannelScans; 3063 } 3064 } 3065 3066 /** 3067 * Increment oneshot scan count for external apps. 3068 */ incrementExternalAppOneshotScanRequestsCount()3069 public void incrementExternalAppOneshotScanRequestsCount() { 3070 synchronized (mLock) { 3071 mWifiLogProto.numExternalAppOneshotScanRequests++; 3072 } 3073 } 3074 /** 3075 * Increment oneshot scan throttle count for external foreground apps. 3076 */ incrementExternalForegroundAppOneshotScanRequestsThrottledCount()3077 public void incrementExternalForegroundAppOneshotScanRequestsThrottledCount() { 3078 synchronized (mLock) { 3079 mWifiLogProto.numExternalForegroundAppOneshotScanRequestsThrottled++; 3080 } 3081 } 3082 3083 /** 3084 * Increment oneshot scan throttle count for external background apps. 3085 */ incrementExternalBackgroundAppOneshotScanRequestsThrottledCount()3086 public void incrementExternalBackgroundAppOneshotScanRequestsThrottledCount() { 3087 synchronized (mLock) { 3088 mWifiLogProto.numExternalBackgroundAppOneshotScanRequestsThrottled++; 3089 } 3090 } 3091 returnCodeToString(int scanReturnCode)3092 private String returnCodeToString(int scanReturnCode) { 3093 switch(scanReturnCode){ 3094 case WifiMetricsProto.WifiLog.SCAN_UNKNOWN: 3095 return "SCAN_UNKNOWN"; 3096 case WifiMetricsProto.WifiLog.SCAN_SUCCESS: 3097 return "SCAN_SUCCESS"; 3098 case WifiMetricsProto.WifiLog.SCAN_FAILURE_INTERRUPTED: 3099 return "SCAN_FAILURE_INTERRUPTED"; 3100 case WifiMetricsProto.WifiLog.SCAN_FAILURE_INVALID_CONFIGURATION: 3101 return "SCAN_FAILURE_INVALID_CONFIGURATION"; 3102 case WifiMetricsProto.WifiLog.FAILURE_WIFI_DISABLED: 3103 return "FAILURE_WIFI_DISABLED"; 3104 default: 3105 return "<UNKNOWN>"; 3106 } 3107 } 3108 3109 /** 3110 * Increment count of scan return code occurrence 3111 * 3112 * @param scanReturnCode Return code from scan attempt WifiMetricsProto.WifiLog.SCAN_X 3113 */ incrementScanReturnEntry(int scanReturnCode, int countToAdd)3114 public void incrementScanReturnEntry(int scanReturnCode, int countToAdd) { 3115 synchronized (mLock) { 3116 if (DBG) Log.v(TAG, "incrementScanReturnEntry " + returnCodeToString(scanReturnCode)); 3117 int entry = mScanReturnEntries.get(scanReturnCode); 3118 entry += countToAdd; 3119 mScanReturnEntries.put(scanReturnCode, entry); 3120 } 3121 } 3122 /** 3123 * Get the count of this scanReturnCode 3124 * @param scanReturnCode that we are getting the count for 3125 */ getScanReturnEntry(int scanReturnCode)3126 public int getScanReturnEntry(int scanReturnCode) { 3127 synchronized (mLock) { 3128 return mScanReturnEntries.get(scanReturnCode); 3129 } 3130 } 3131 wifiSystemStateToString(int state)3132 private String wifiSystemStateToString(int state) { 3133 switch(state){ 3134 case WifiMetricsProto.WifiLog.WIFI_UNKNOWN: 3135 return "WIFI_UNKNOWN"; 3136 case WifiMetricsProto.WifiLog.WIFI_DISABLED: 3137 return "WIFI_DISABLED"; 3138 case WifiMetricsProto.WifiLog.WIFI_DISCONNECTED: 3139 return "WIFI_DISCONNECTED"; 3140 case WifiMetricsProto.WifiLog.WIFI_ASSOCIATED: 3141 return "WIFI_ASSOCIATED"; 3142 default: 3143 return "default"; 3144 } 3145 } 3146 3147 /** 3148 * Increments the count of scans initiated by each wifi state, accounts for screenOn/Off 3149 * 3150 * @param state State of the system when scan was initiated, see WifiMetricsProto.WifiLog.WIFI_X 3151 * @param screenOn Is the screen on 3152 */ incrementWifiSystemScanStateCount(int state, boolean screenOn)3153 public void incrementWifiSystemScanStateCount(int state, boolean screenOn) { 3154 synchronized (mLock) { 3155 if (DBG) { 3156 Log.v(TAG, "incrementWifiSystemScanStateCount " + wifiSystemStateToString(state) 3157 + " " + screenOn); 3158 } 3159 int index = (state * 2) + (screenOn ? SCREEN_ON : SCREEN_OFF); 3160 int entry = mWifiSystemStateEntries.get(index); 3161 entry++; 3162 mWifiSystemStateEntries.put(index, entry); 3163 } 3164 } 3165 3166 /** 3167 * Get the count of this system State Entry 3168 */ getSystemStateCount(int state, boolean screenOn)3169 public int getSystemStateCount(int state, boolean screenOn) { 3170 synchronized (mLock) { 3171 int index = state * 2 + (screenOn ? SCREEN_ON : SCREEN_OFF); 3172 return mWifiSystemStateEntries.get(index); 3173 } 3174 } 3175 3176 /** 3177 * Increment number of times the Watchdog of Last Resort triggered, resetting the wifi stack 3178 */ incrementNumLastResortWatchdogTriggers()3179 public void incrementNumLastResortWatchdogTriggers() { 3180 synchronized (mLock) { 3181 mWifiLogProto.numLastResortWatchdogTriggers++; 3182 } 3183 } 3184 /** 3185 * @param count number of networks over bad association threshold when watchdog triggered 3186 */ addCountToNumLastResortWatchdogBadAssociationNetworksTotal(int count)3187 public void addCountToNumLastResortWatchdogBadAssociationNetworksTotal(int count) { 3188 synchronized (mLock) { 3189 mWifiLogProto.numLastResortWatchdogBadAssociationNetworksTotal += count; 3190 } 3191 } 3192 /** 3193 * @param count number of networks over bad authentication threshold when watchdog triggered 3194 */ addCountToNumLastResortWatchdogBadAuthenticationNetworksTotal(int count)3195 public void addCountToNumLastResortWatchdogBadAuthenticationNetworksTotal(int count) { 3196 synchronized (mLock) { 3197 mWifiLogProto.numLastResortWatchdogBadAuthenticationNetworksTotal += count; 3198 } 3199 } 3200 /** 3201 * @param count number of networks over bad dhcp threshold when watchdog triggered 3202 */ addCountToNumLastResortWatchdogBadDhcpNetworksTotal(int count)3203 public void addCountToNumLastResortWatchdogBadDhcpNetworksTotal(int count) { 3204 synchronized (mLock) { 3205 mWifiLogProto.numLastResortWatchdogBadDhcpNetworksTotal += count; 3206 } 3207 } 3208 /** 3209 * @param count number of networks over bad other threshold when watchdog triggered 3210 */ addCountToNumLastResortWatchdogBadOtherNetworksTotal(int count)3211 public void addCountToNumLastResortWatchdogBadOtherNetworksTotal(int count) { 3212 synchronized (mLock) { 3213 mWifiLogProto.numLastResortWatchdogBadOtherNetworksTotal += count; 3214 } 3215 } 3216 /** 3217 * @param count number of networks seen when watchdog triggered 3218 */ addCountToNumLastResortWatchdogAvailableNetworksTotal(int count)3219 public void addCountToNumLastResortWatchdogAvailableNetworksTotal(int count) { 3220 synchronized (mLock) { 3221 mWifiLogProto.numLastResortWatchdogAvailableNetworksTotal += count; 3222 } 3223 } 3224 /** 3225 * Increment count of triggers with atleast one bad association network 3226 */ incrementNumLastResortWatchdogTriggersWithBadAssociation()3227 public void incrementNumLastResortWatchdogTriggersWithBadAssociation() { 3228 synchronized (mLock) { 3229 mWifiLogProto.numLastResortWatchdogTriggersWithBadAssociation++; 3230 } 3231 } 3232 /** 3233 * Increment count of triggers with atleast one bad authentication network 3234 */ incrementNumLastResortWatchdogTriggersWithBadAuthentication()3235 public void incrementNumLastResortWatchdogTriggersWithBadAuthentication() { 3236 synchronized (mLock) { 3237 mWifiLogProto.numLastResortWatchdogTriggersWithBadAuthentication++; 3238 } 3239 } 3240 /** 3241 * Increment count of triggers with atleast one bad dhcp network 3242 */ incrementNumLastResortWatchdogTriggersWithBadDhcp()3243 public void incrementNumLastResortWatchdogTriggersWithBadDhcp() { 3244 synchronized (mLock) { 3245 mWifiLogProto.numLastResortWatchdogTriggersWithBadDhcp++; 3246 } 3247 } 3248 /** 3249 * Increment count of triggers with atleast one bad other network 3250 */ incrementNumLastResortWatchdogTriggersWithBadOther()3251 public void incrementNumLastResortWatchdogTriggersWithBadOther() { 3252 synchronized (mLock) { 3253 mWifiLogProto.numLastResortWatchdogTriggersWithBadOther++; 3254 } 3255 } 3256 3257 /** 3258 * Increment number of times connectivity watchdog confirmed pno is working 3259 */ incrementNumConnectivityWatchdogPnoGood()3260 public void incrementNumConnectivityWatchdogPnoGood() { 3261 synchronized (mLock) { 3262 mWifiLogProto.numConnectivityWatchdogPnoGood++; 3263 } 3264 } 3265 /** 3266 * Increment number of times connectivity watchdog found pno not working 3267 */ incrementNumConnectivityWatchdogPnoBad()3268 public void incrementNumConnectivityWatchdogPnoBad() { 3269 synchronized (mLock) { 3270 mWifiLogProto.numConnectivityWatchdogPnoBad++; 3271 } 3272 } 3273 /** 3274 * Increment number of times connectivity watchdog confirmed background scan is working 3275 */ incrementNumConnectivityWatchdogBackgroundGood()3276 public void incrementNumConnectivityWatchdogBackgroundGood() { 3277 synchronized (mLock) { 3278 mWifiLogProto.numConnectivityWatchdogBackgroundGood++; 3279 } 3280 } 3281 /** 3282 * Increment number of times connectivity watchdog found background scan not working 3283 */ incrementNumConnectivityWatchdogBackgroundBad()3284 public void incrementNumConnectivityWatchdogBackgroundBad() { 3285 synchronized (mLock) { 3286 mWifiLogProto.numConnectivityWatchdogBackgroundBad++; 3287 } 3288 } 3289 3290 /** 3291 * Increment various poll related metrics, and cache performance data for StaEvent logging 3292 */ handlePollResult(String ifaceName, WifiInfo wifiInfo)3293 public void handlePollResult(String ifaceName, WifiInfo wifiInfo) { 3294 if (!isPrimary(ifaceName)) { 3295 return; 3296 } 3297 mLastPollRssi = wifiInfo.getRssi(); 3298 mLastPollLinkSpeed = wifiInfo.getLinkSpeed(); 3299 mLastPollFreq = wifiInfo.getFrequency(); 3300 incrementRssiPollRssiCount(mLastPollFreq, mLastPollRssi); 3301 incrementLinkSpeedCount(mLastPollLinkSpeed, mLastPollRssi); 3302 mLastPollRxLinkSpeed = wifiInfo.getRxLinkSpeedMbps(); 3303 incrementTxLinkSpeedBandCount(mLastPollLinkSpeed, mLastPollFreq); 3304 incrementRxLinkSpeedBandCount(mLastPollRxLinkSpeed, mLastPollFreq); 3305 mWifiStatusBuilder.setRssi(mLastPollRssi); 3306 mWifiStatusBuilder.setNetworkId(wifiInfo.getNetworkId()); 3307 } 3308 3309 /** 3310 * Increment occurence count of RSSI level from RSSI poll for the given frequency. 3311 * @param frequency (MHz) 3312 * @param rssi 3313 */ 3314 @VisibleForTesting incrementRssiPollRssiCount(int frequency, int rssi)3315 public void incrementRssiPollRssiCount(int frequency, int rssi) { 3316 if (!(rssi >= MIN_RSSI_POLL && rssi <= MAX_RSSI_POLL)) { 3317 return; 3318 } 3319 synchronized (mLock) { 3320 if (!mRssiPollCountsMap.containsKey(frequency)) { 3321 mRssiPollCountsMap.put(frequency, new SparseIntArray()); 3322 } 3323 SparseIntArray sparseIntArray = mRssiPollCountsMap.get(frequency); 3324 int count = sparseIntArray.get(rssi); 3325 sparseIntArray.put(rssi, count + 1); 3326 maybeIncrementRssiDeltaCount(rssi - mScanResultRssi); 3327 } 3328 } 3329 3330 /** 3331 * Increment occurence count of difference between scan result RSSI and the first RSSI poll. 3332 * Ignores rssi values outside the bounds of [MIN_RSSI_DELTA, MAX_RSSI_DELTA] 3333 * mLock must be held when calling this method. 3334 */ maybeIncrementRssiDeltaCount(int rssi)3335 private void maybeIncrementRssiDeltaCount(int rssi) { 3336 // Check if this RSSI poll is close enough to a scan result RSSI to log a delta value 3337 if (mScanResultRssiTimestampMillis >= 0) { 3338 long timeDelta = mClock.getElapsedSinceBootMillis() - mScanResultRssiTimestampMillis; 3339 if (timeDelta <= TIMEOUT_RSSI_DELTA_MILLIS) { 3340 if (rssi >= MIN_RSSI_DELTA && rssi <= MAX_RSSI_DELTA) { 3341 int count = mRssiDeltaCounts.get(rssi); 3342 mRssiDeltaCounts.put(rssi, count + 1); 3343 } 3344 } 3345 mScanResultRssiTimestampMillis = -1; 3346 } 3347 } 3348 3349 /** 3350 * Increment occurrence count of link speed. 3351 * Ignores link speed values that are lower than MIN_LINK_SPEED_MBPS 3352 * and rssi values outside the bounds of [MIN_RSSI_POLL, MAX_RSSI_POLL] 3353 */ 3354 @VisibleForTesting incrementLinkSpeedCount(int linkSpeed, int rssi)3355 public void incrementLinkSpeedCount(int linkSpeed, int rssi) { 3356 if (!(mContext.getResources().getBoolean(R.bool.config_wifiLinkSpeedMetricsEnabled) 3357 && linkSpeed >= MIN_LINK_SPEED_MBPS 3358 && rssi >= MIN_RSSI_POLL 3359 && rssi <= MAX_RSSI_POLL)) { 3360 return; 3361 } 3362 synchronized (mLock) { 3363 LinkSpeedCount linkSpeedCount = mLinkSpeedCounts.get(linkSpeed); 3364 if (linkSpeedCount == null) { 3365 linkSpeedCount = new LinkSpeedCount(); 3366 linkSpeedCount.linkSpeedMbps = linkSpeed; 3367 mLinkSpeedCounts.put(linkSpeed, linkSpeedCount); 3368 } 3369 linkSpeedCount.count++; 3370 linkSpeedCount.rssiSumDbm += Math.abs(rssi); 3371 linkSpeedCount.rssiSumOfSquaresDbmSq += rssi * rssi; 3372 } 3373 } 3374 3375 /** 3376 * Increment occurrence count of Tx link speed for operating sub-band 3377 * Ignores link speed values that are lower than MIN_LINK_SPEED_MBPS 3378 * @param txLinkSpeed PHY layer Tx link speed in Mbps 3379 * @param frequency Channel frequency of beacon frames in MHz 3380 */ 3381 @VisibleForTesting incrementTxLinkSpeedBandCount(int txLinkSpeed, int frequency)3382 public void incrementTxLinkSpeedBandCount(int txLinkSpeed, int frequency) { 3383 if (!(mContext.getResources().getBoolean(R.bool.config_wifiLinkSpeedMetricsEnabled) 3384 && txLinkSpeed >= MIN_LINK_SPEED_MBPS)) { 3385 return; 3386 } 3387 synchronized (mLock) { 3388 if (ScanResult.is24GHz(frequency)) { 3389 mTxLinkSpeedCount2g.increment(txLinkSpeed); 3390 } else if (frequency <= KnownBandsChannelHelper.BAND_5_GHZ_LOW_END_FREQ) { 3391 mTxLinkSpeedCount5gLow.increment(txLinkSpeed); 3392 } else if (frequency <= KnownBandsChannelHelper.BAND_5_GHZ_MID_END_FREQ) { 3393 mTxLinkSpeedCount5gMid.increment(txLinkSpeed); 3394 } else if (frequency <= KnownBandsChannelHelper.BAND_5_GHZ_HIGH_END_FREQ) { 3395 mTxLinkSpeedCount5gHigh.increment(txLinkSpeed); 3396 } else if (frequency <= KnownBandsChannelHelper.BAND_6_GHZ_LOW_END_FREQ) { 3397 mTxLinkSpeedCount6gLow.increment(txLinkSpeed); 3398 } else if (frequency <= KnownBandsChannelHelper.BAND_6_GHZ_MID_END_FREQ) { 3399 mTxLinkSpeedCount6gMid.increment(txLinkSpeed); 3400 } else if (frequency <= KnownBandsChannelHelper.BAND_6_GHZ_HIGH_END_FREQ) { 3401 mTxLinkSpeedCount6gHigh.increment(txLinkSpeed); 3402 } 3403 } 3404 } 3405 3406 /** 3407 * Increment occurrence count of Rx link speed for operating sub-band 3408 * Ignores link speed values that are lower than MIN_LINK_SPEED_MBPS 3409 * @param rxLinkSpeed PHY layer Tx link speed in Mbps 3410 * @param frequency Channel frequency of beacon frames in MHz 3411 */ 3412 @VisibleForTesting incrementRxLinkSpeedBandCount(int rxLinkSpeed, int frequency)3413 public void incrementRxLinkSpeedBandCount(int rxLinkSpeed, int frequency) { 3414 if (!(mContext.getResources().getBoolean(R.bool.config_wifiLinkSpeedMetricsEnabled) 3415 && rxLinkSpeed >= MIN_LINK_SPEED_MBPS)) { 3416 return; 3417 } 3418 synchronized (mLock) { 3419 if (ScanResult.is24GHz(frequency)) { 3420 mRxLinkSpeedCount2g.increment(rxLinkSpeed); 3421 } else if (frequency <= KnownBandsChannelHelper.BAND_5_GHZ_LOW_END_FREQ) { 3422 mRxLinkSpeedCount5gLow.increment(rxLinkSpeed); 3423 } else if (frequency <= KnownBandsChannelHelper.BAND_5_GHZ_MID_END_FREQ) { 3424 mRxLinkSpeedCount5gMid.increment(rxLinkSpeed); 3425 } else if (frequency <= KnownBandsChannelHelper.BAND_5_GHZ_HIGH_END_FREQ) { 3426 mRxLinkSpeedCount5gHigh.increment(rxLinkSpeed); 3427 } else if (frequency <= KnownBandsChannelHelper.BAND_6_GHZ_LOW_END_FREQ) { 3428 mRxLinkSpeedCount6gLow.increment(rxLinkSpeed); 3429 } else if (frequency <= KnownBandsChannelHelper.BAND_6_GHZ_MID_END_FREQ) { 3430 mRxLinkSpeedCount6gMid.increment(rxLinkSpeed); 3431 } else if (frequency <= KnownBandsChannelHelper.BAND_6_GHZ_HIGH_END_FREQ) { 3432 mRxLinkSpeedCount6gHigh.increment(rxLinkSpeed); 3433 } 3434 } 3435 } 3436 3437 /** 3438 * Increment occurrence count of channel utilization 3439 * @param channelUtilization Channel utilization of current network 3440 * @param frequency Channel frequency of current network 3441 */ 3442 @VisibleForTesting incrementChannelUtilizationCount(int channelUtilization, int frequency)3443 public void incrementChannelUtilizationCount(int channelUtilization, int frequency) { 3444 if (channelUtilization < InformationElementUtil.BssLoad.MIN_CHANNEL_UTILIZATION 3445 || channelUtilization > InformationElementUtil.BssLoad.MAX_CHANNEL_UTILIZATION) { 3446 return; 3447 } 3448 synchronized (mLock) { 3449 if (ScanResult.is24GHz(frequency)) { 3450 mChannelUtilizationHistogram2G.increment(channelUtilization); 3451 } else { 3452 mChannelUtilizationHistogramAbove2G.increment(channelUtilization); 3453 } 3454 } 3455 } 3456 3457 /** 3458 * Increment occurrence count of Tx and Rx throughput 3459 * @param txThroughputKbps Tx throughput of current network in Kbps 3460 * @param rxThroughputKbps Rx throughput of current network in Kbps 3461 * @param frequency Channel frequency of current network in MHz 3462 */ 3463 @VisibleForTesting incrementThroughputKbpsCount(int txThroughputKbps, int rxThroughputKbps, int frequency)3464 public void incrementThroughputKbpsCount(int txThroughputKbps, int rxThroughputKbps, 3465 int frequency) { 3466 synchronized (mLock) { 3467 if (ScanResult.is24GHz(frequency)) { 3468 if (txThroughputKbps >= 0) { 3469 mTxThroughputMbpsHistogram2G.increment(txThroughputKbps / 1000); 3470 } 3471 if (rxThroughputKbps >= 0) { 3472 mRxThroughputMbpsHistogram2G.increment(rxThroughputKbps / 1000); 3473 } 3474 } else { 3475 if (txThroughputKbps >= 0) { 3476 mTxThroughputMbpsHistogramAbove2G.increment(txThroughputKbps / 1000); 3477 } 3478 if (rxThroughputKbps >= 0) { 3479 mRxThroughputMbpsHistogramAbove2G.increment(rxThroughputKbps / 1000); 3480 } 3481 } 3482 mWifiStatusBuilder.setEstimatedTxKbps(txThroughputKbps); 3483 mWifiStatusBuilder.setEstimatedRxKbps(rxThroughputKbps); 3484 } 3485 } 3486 3487 /** 3488 * Increment count of Watchdog successes. 3489 */ incrementNumLastResortWatchdogSuccesses()3490 public void incrementNumLastResortWatchdogSuccesses() { 3491 synchronized (mLock) { 3492 mWifiLogProto.numLastResortWatchdogSuccesses++; 3493 } 3494 } 3495 3496 /** 3497 * Increment the count of network connection failures that happened after watchdog has been 3498 * triggered. 3499 */ incrementWatchdogTotalConnectionFailureCountAfterTrigger()3500 public void incrementWatchdogTotalConnectionFailureCountAfterTrigger() { 3501 synchronized (mLock) { 3502 mWifiLogProto.watchdogTotalConnectionFailureCountAfterTrigger++; 3503 } 3504 } 3505 3506 /** 3507 * Sets the time taken for wifi to connect after a watchdog triggers a restart. 3508 * @param milliseconds 3509 */ setWatchdogSuccessTimeDurationMs(long ms)3510 public void setWatchdogSuccessTimeDurationMs(long ms) { 3511 synchronized (mLock) { 3512 mWifiLogProto.watchdogTriggerToConnectionSuccessDurationMs = ms; 3513 } 3514 } 3515 3516 /** 3517 * Increments the count of alerts by alert reason. 3518 * 3519 * @param reason The cause of the alert. The reason values are driver-specific. 3520 */ incrementAlertReasonCount(int reason)3521 private void incrementAlertReasonCount(int reason) { 3522 if (reason > WifiLoggerHal.WIFI_ALERT_REASON_MAX 3523 || reason < WifiLoggerHal.WIFI_ALERT_REASON_MIN) { 3524 reason = WifiLoggerHal.WIFI_ALERT_REASON_RESERVED; 3525 } 3526 synchronized (mLock) { 3527 int alertCount = mWifiAlertReasonCounts.get(reason); 3528 mWifiAlertReasonCounts.put(reason, alertCount + 1); 3529 } 3530 } 3531 3532 /** 3533 * Counts all the different types of networks seen in a set of scan results 3534 */ countScanResults(List<ScanDetail> scanDetails)3535 public void countScanResults(List<ScanDetail> scanDetails) { 3536 if (scanDetails == null) { 3537 return; 3538 } 3539 int totalResults = 0; 3540 int openNetworks = 0; 3541 int personalNetworks = 0; 3542 int enterpriseNetworks = 0; 3543 int hiddenNetworks = 0; 3544 int hotspot2r1Networks = 0; 3545 int hotspot2r2Networks = 0; 3546 int hotspot2r3Networks = 0; 3547 int enhacedOpenNetworks = 0; 3548 int wpa3PersonalNetworks = 0; 3549 int wpa3EnterpriseNetworks = 0; 3550 int wapiPersonalNetworks = 0; 3551 int wapiEnterpriseNetworks = 0; 3552 int mboSupportedNetworks = 0; 3553 int mboCellularDataAwareNetworks = 0; 3554 int oceSupportedNetworks = 0; 3555 int filsSupportedNetworks = 0; 3556 int band6gNetworks = 0; 3557 int band6gPscNetworks = 0; 3558 int standard11axNetworks = 0; 3559 3560 for (ScanDetail scanDetail : scanDetails) { 3561 NetworkDetail networkDetail = scanDetail.getNetworkDetail(); 3562 ScanResult scanResult = scanDetail.getScanResult(); 3563 totalResults++; 3564 if (networkDetail != null) { 3565 if (networkDetail.isHiddenBeaconFrame()) { 3566 hiddenNetworks++; 3567 } 3568 if (networkDetail.getHSRelease() != null) { 3569 if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R1) { 3570 hotspot2r1Networks++; 3571 } else if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R2) { 3572 hotspot2r2Networks++; 3573 } else if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R3) { 3574 hotspot2r3Networks++; 3575 } 3576 } 3577 if (networkDetail.isMboSupported()) { 3578 mboSupportedNetworks++; 3579 if (networkDetail.isMboCellularDataAware()) { 3580 mboCellularDataAwareNetworks++; 3581 } 3582 if (networkDetail.isOceSupported()) { 3583 oceSupportedNetworks++; 3584 } 3585 } 3586 if (networkDetail.getWifiMode() == InformationElementUtil.WifiMode.MODE_11AX) { 3587 standard11axNetworks++; 3588 } 3589 } 3590 if (scanResult != null && scanResult.capabilities != null) { 3591 if (ScanResultUtil.isScanResultForFilsSha256Network(scanResult) 3592 || ScanResultUtil.isScanResultForFilsSha384Network(scanResult)) { 3593 filsSupportedNetworks++; 3594 } 3595 if (scanResult.is6GHz()) { 3596 band6gNetworks++; 3597 if (scanResult.is6GhzPsc()) { 3598 band6gPscNetworks++; 3599 } 3600 } 3601 if (ScanResultUtil.isScanResultForEapSuiteBNetwork(scanResult) 3602 || ScanResultUtil.isScanResultForWpa3EnterpriseTransitionNetwork(scanResult) 3603 || ScanResultUtil.isScanResultForWpa3EnterpriseOnlyNetwork(scanResult)) { 3604 wpa3EnterpriseNetworks++; 3605 } else if (ScanResultUtil.isScanResultForWapiPskNetwork(scanResult)) { 3606 wapiPersonalNetworks++; 3607 } else if (ScanResultUtil.isScanResultForWapiCertNetwork(scanResult)) { 3608 wapiEnterpriseNetworks++; 3609 } else if (ScanResultUtil.isScanResultForWpa2EnterpriseOnlyNetwork(scanResult)) { 3610 enterpriseNetworks++; 3611 } else if (ScanResultUtil.isScanResultForSaeNetwork(scanResult)) { 3612 wpa3PersonalNetworks++; 3613 } else if (ScanResultUtil.isScanResultForPskNetwork(scanResult) 3614 || ScanResultUtil.isScanResultForWepNetwork(scanResult)) { 3615 personalNetworks++; 3616 } else if (ScanResultUtil.isScanResultForOweNetwork(scanResult)) { 3617 enhacedOpenNetworks++; 3618 } else { 3619 openNetworks++; 3620 } 3621 } 3622 } 3623 synchronized (mLock) { 3624 mWifiLogProto.numTotalScanResults += totalResults; 3625 mWifiLogProto.numOpenNetworkScanResults += openNetworks; 3626 mWifiLogProto.numLegacyPersonalNetworkScanResults += personalNetworks; 3627 mWifiLogProto.numLegacyEnterpriseNetworkScanResults += enterpriseNetworks; 3628 mWifiLogProto.numEnhancedOpenNetworkScanResults += enhacedOpenNetworks; 3629 mWifiLogProto.numWpa3PersonalNetworkScanResults += wpa3PersonalNetworks; 3630 mWifiLogProto.numWpa3EnterpriseNetworkScanResults += wpa3EnterpriseNetworks; 3631 mWifiLogProto.numWapiPersonalNetworkScanResults += wapiPersonalNetworks; 3632 mWifiLogProto.numWapiEnterpriseNetworkScanResults += wapiEnterpriseNetworks; 3633 mWifiLogProto.numHiddenNetworkScanResults += hiddenNetworks; 3634 mWifiLogProto.numHotspot2R1NetworkScanResults += hotspot2r1Networks; 3635 mWifiLogProto.numHotspot2R2NetworkScanResults += hotspot2r2Networks; 3636 mWifiLogProto.numHotspot2R3NetworkScanResults += hotspot2r3Networks; 3637 mWifiLogProto.numMboSupportedNetworkScanResults += mboSupportedNetworks; 3638 mWifiLogProto.numMboCellularDataAwareNetworkScanResults += mboCellularDataAwareNetworks; 3639 mWifiLogProto.numOceSupportedNetworkScanResults += oceSupportedNetworks; 3640 mWifiLogProto.numFilsSupportedNetworkScanResults += filsSupportedNetworks; 3641 mWifiLogProto.num11AxNetworkScanResults += standard11axNetworks; 3642 mWifiLogProto.num6GNetworkScanResults += band6gNetworks; 3643 mWifiLogProto.num6GPscNetworkScanResults += band6gPscNetworks; 3644 mWifiLogProto.numScans++; 3645 } 3646 } 3647 3648 private boolean mWifiWins = false; // Based on scores, use wifi instead of mobile data? 3649 // Based on Wifi usability scores. use wifi instead of mobile data? 3650 private boolean mWifiWinsUsabilityScore = false; 3651 3652 /** 3653 * Increments occurence of a particular wifi score calculated 3654 * in WifiScoreReport by current connected network. Scores are bounded 3655 * within [MIN_WIFI_SCORE, MAX_WIFI_SCORE] to limit size of SparseArray. 3656 * 3657 * Also records events when the current score breaches significant thresholds. 3658 */ incrementWifiScoreCount(String ifaceName, int score)3659 public void incrementWifiScoreCount(String ifaceName, int score) { 3660 if (score < MIN_WIFI_SCORE || score > MAX_WIFI_SCORE) { 3661 return; 3662 } 3663 synchronized (mLock) { 3664 int count = mWifiScoreCounts.get(score); 3665 mWifiScoreCounts.put(score, count + 1); 3666 3667 boolean wifiWins = mWifiWins; 3668 if (mWifiWins && score < LOW_WIFI_SCORE) { 3669 wifiWins = false; 3670 } else if (!mWifiWins && score > LOW_WIFI_SCORE) { 3671 wifiWins = true; 3672 } 3673 mLastScore = score; 3674 mLastScoreNoReset = score; 3675 if (wifiWins != mWifiWins) { 3676 mWifiWins = wifiWins; 3677 StaEvent event = new StaEvent(); 3678 event.type = StaEvent.TYPE_SCORE_BREACH; 3679 addStaEvent(ifaceName, event); 3680 // Only record the first score breach by checking whether mScoreBreachLowTimeMillis 3681 // has been set to -1 3682 if (!wifiWins && mScoreBreachLowTimeMillis == -1) { 3683 mScoreBreachLowTimeMillis = mClock.getElapsedSinceBootMillis(); 3684 } 3685 } 3686 } 3687 } 3688 3689 /** 3690 * Increments occurence of the results from attempting to start SoftAp. 3691 * Maps the |result| and WifiManager |failureCode| constant to proto defined SoftApStartResult 3692 * codes. 3693 */ incrementSoftApStartResult(boolean result, int failureCode)3694 public void incrementSoftApStartResult(boolean result, int failureCode) { 3695 synchronized (mLock) { 3696 if (result) { 3697 int count = mSoftApManagerReturnCodeCounts.get( 3698 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_STARTED_SUCCESSFULLY); 3699 mSoftApManagerReturnCodeCounts.put( 3700 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_STARTED_SUCCESSFULLY, 3701 count + 1); 3702 return; 3703 } 3704 3705 // now increment failure modes - if not explicitly handled, dump into the general 3706 // error bucket. 3707 if (failureCode == WifiManager.SAP_START_FAILURE_NO_CHANNEL) { 3708 int count = mSoftApManagerReturnCodeCounts.get( 3709 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_NO_CHANNEL); 3710 mSoftApManagerReturnCodeCounts.put( 3711 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_NO_CHANNEL, 3712 count + 1); 3713 } else if (failureCode == WifiManager.SAP_START_FAILURE_UNSUPPORTED_CONFIGURATION) { 3714 int count = mSoftApManagerReturnCodeCounts.get( 3715 WifiMetricsProto.SoftApReturnCodeCount 3716 .SOFT_AP_FAILED_UNSUPPORTED_CONFIGURATION); 3717 mSoftApManagerReturnCodeCounts.put( 3718 WifiMetricsProto.SoftApReturnCodeCount 3719 .SOFT_AP_FAILED_UNSUPPORTED_CONFIGURATION, 3720 count + 1); 3721 } else { 3722 // failure mode not tracked at this time... count as a general error for now. 3723 int count = mSoftApManagerReturnCodeCounts.get( 3724 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_GENERAL_ERROR); 3725 mSoftApManagerReturnCodeCounts.put( 3726 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_GENERAL_ERROR, 3727 count + 1); 3728 } 3729 } 3730 } 3731 3732 /** 3733 * Adds a record indicating the current up state of soft AP 3734 */ addSoftApUpChangedEvent(boolean isUp, int mode, long defaultShutdownTimeoutMillis, boolean isBridged)3735 public void addSoftApUpChangedEvent(boolean isUp, int mode, long defaultShutdownTimeoutMillis, 3736 boolean isBridged) { 3737 int numOfEventNeedToAdd = isBridged && isUp ? 2 : 1; 3738 for (int i = 0; i < numOfEventNeedToAdd; i++) { 3739 SoftApConnectedClientsEvent event = new SoftApConnectedClientsEvent(); 3740 if (isUp) { 3741 event.eventType = isBridged ? SoftApConnectedClientsEvent.DUAL_AP_BOTH_INSTANCES_UP 3742 : SoftApConnectedClientsEvent.SOFT_AP_UP; 3743 } else { 3744 event.eventType = SoftApConnectedClientsEvent.SOFT_AP_DOWN; 3745 } 3746 event.numConnectedClients = 0; 3747 event.defaultShutdownTimeoutSetting = defaultShutdownTimeoutMillis; 3748 addSoftApConnectedClientsEvent(event, mode); 3749 } 3750 } 3751 3752 /** 3753 * Adds a record indicating the one of the dual AP instances is down. 3754 */ addSoftApInstanceDownEventInDualMode(int mode, @NonNull SoftApInfo info)3755 public void addSoftApInstanceDownEventInDualMode(int mode, @NonNull SoftApInfo info) { 3756 SoftApConnectedClientsEvent event = new SoftApConnectedClientsEvent(); 3757 event.eventType = SoftApConnectedClientsEvent.DUAL_AP_ONE_INSTANCE_DOWN; 3758 event.channelFrequency = info.getFrequency(); 3759 event.channelBandwidth = info.getBandwidth(); 3760 event.generation = info.getWifiStandardInternal(); 3761 addSoftApConnectedClientsEvent(event, mode); 3762 } 3763 3764 /** 3765 * Adds a record for current number of associated stations to soft AP 3766 */ addSoftApNumAssociatedStationsChangedEvent(int numTotalStations, int numStationsOnCurrentFrequency, int mode, @Nullable SoftApInfo info)3767 public void addSoftApNumAssociatedStationsChangedEvent(int numTotalStations, 3768 int numStationsOnCurrentFrequency, int mode, @Nullable SoftApInfo info) { 3769 SoftApConnectedClientsEvent event = new SoftApConnectedClientsEvent(); 3770 event.eventType = SoftApConnectedClientsEvent.NUM_CLIENTS_CHANGED; 3771 if (info != null) { 3772 event.channelFrequency = info.getFrequency(); 3773 event.channelBandwidth = info.getBandwidth(); 3774 event.generation = info.getWifiStandardInternal(); 3775 } 3776 event.numConnectedClients = numTotalStations; 3777 event.numConnectedClientsOnCurrentFrequency = numStationsOnCurrentFrequency; 3778 addSoftApConnectedClientsEvent(event, mode); 3779 } 3780 3781 /** 3782 * Adds a record to the corresponding event list based on mode param 3783 */ addSoftApConnectedClientsEvent(SoftApConnectedClientsEvent event, int mode)3784 private void addSoftApConnectedClientsEvent(SoftApConnectedClientsEvent event, int mode) { 3785 synchronized (mLock) { 3786 List<SoftApConnectedClientsEvent> softApEventList; 3787 switch (mode) { 3788 case WifiManager.IFACE_IP_MODE_TETHERED: 3789 softApEventList = mSoftApEventListTethered; 3790 break; 3791 case WifiManager.IFACE_IP_MODE_LOCAL_ONLY: 3792 softApEventList = mSoftApEventListLocalOnly; 3793 break; 3794 default: 3795 return; 3796 } 3797 3798 if (softApEventList.size() > MAX_NUM_SOFT_AP_EVENTS) { 3799 return; 3800 } 3801 3802 event.timeStampMillis = mClock.getElapsedSinceBootMillis(); 3803 softApEventList.add(event); 3804 } 3805 } 3806 3807 /** 3808 * Updates current soft AP events with channel info 3809 */ addSoftApChannelSwitchedEvent(List<SoftApInfo> infos, int mode, boolean isBridged)3810 public void addSoftApChannelSwitchedEvent(List<SoftApInfo> infos, int mode, boolean isBridged) { 3811 synchronized (mLock) { 3812 int numOfEventNeededToUpdate = infos.size(); 3813 if (isBridged && numOfEventNeededToUpdate == 1) { 3814 // Ignore the channel info update when only 1 info in bridged mode because it means 3815 // that one of the instance was been shutdown. 3816 return; 3817 } 3818 int apUpEvent = isBridged ? SoftApConnectedClientsEvent.DUAL_AP_BOTH_INSTANCES_UP 3819 : SoftApConnectedClientsEvent.SOFT_AP_UP; 3820 List<SoftApConnectedClientsEvent> softApEventList; 3821 switch (mode) { 3822 case WifiManager.IFACE_IP_MODE_TETHERED: 3823 softApEventList = mSoftApEventListTethered; 3824 break; 3825 case WifiManager.IFACE_IP_MODE_LOCAL_ONLY: 3826 softApEventList = mSoftApEventListLocalOnly; 3827 break; 3828 default: 3829 return; 3830 } 3831 3832 for (int index = softApEventList.size() - 1; 3833 index >= 0 && numOfEventNeededToUpdate != 0; index--) { 3834 SoftApConnectedClientsEvent event = softApEventList.get(index); 3835 if (event != null && event.eventType == apUpEvent) { 3836 int infoIndex = numOfEventNeededToUpdate - 1; 3837 event.channelFrequency = infos.get(infoIndex).getFrequency(); 3838 event.channelBandwidth = infos.get(infoIndex).getBandwidth(); 3839 event.generation = infos.get(infoIndex).getWifiStandardInternal(); 3840 numOfEventNeededToUpdate--; 3841 } 3842 } 3843 } 3844 } 3845 3846 /** 3847 * Updates current soft AP events with softap configuration 3848 */ updateSoftApConfiguration(SoftApConfiguration config, int mode, boolean isBridged)3849 public void updateSoftApConfiguration(SoftApConfiguration config, int mode, boolean isBridged) { 3850 synchronized (mLock) { 3851 List<SoftApConnectedClientsEvent> softApEventList; 3852 switch (mode) { 3853 case WifiManager.IFACE_IP_MODE_TETHERED: 3854 softApEventList = mSoftApEventListTethered; 3855 break; 3856 case WifiManager.IFACE_IP_MODE_LOCAL_ONLY: 3857 softApEventList = mSoftApEventListLocalOnly; 3858 break; 3859 default: 3860 return; 3861 } 3862 3863 int numOfEventNeededToUpdate = isBridged ? 2 : 1; 3864 int apUpEvent = isBridged ? SoftApConnectedClientsEvent.DUAL_AP_BOTH_INSTANCES_UP 3865 : SoftApConnectedClientsEvent.SOFT_AP_UP; 3866 3867 for (int index = softApEventList.size() - 1; 3868 index >= 0 && numOfEventNeededToUpdate != 0; index--) { 3869 SoftApConnectedClientsEvent event = softApEventList.get(index); 3870 if (event != null && event.eventType == apUpEvent) { 3871 event.maxNumClientsSettingInSoftapConfiguration = 3872 config.getMaxNumberOfClients(); 3873 event.shutdownTimeoutSettingInSoftapConfiguration = 3874 config.getShutdownTimeoutMillis(); 3875 event.clientControlIsEnabled = config.isClientControlByUserEnabled(); 3876 numOfEventNeededToUpdate--; 3877 } 3878 } 3879 } 3880 } 3881 3882 /** 3883 * Updates current soft AP events with softap capability 3884 */ updateSoftApCapability(SoftApCapability capability, int mode, boolean isBridged)3885 public void updateSoftApCapability(SoftApCapability capability, int mode, boolean isBridged) { 3886 synchronized (mLock) { 3887 List<SoftApConnectedClientsEvent> softApEventList; 3888 switch (mode) { 3889 case WifiManager.IFACE_IP_MODE_TETHERED: 3890 softApEventList = mSoftApEventListTethered; 3891 break; 3892 case WifiManager.IFACE_IP_MODE_LOCAL_ONLY: 3893 softApEventList = mSoftApEventListLocalOnly; 3894 break; 3895 default: 3896 return; 3897 } 3898 3899 int numOfEventNeededToUpdate = isBridged ? 2 : 1; 3900 int apUpEvent = isBridged ? SoftApConnectedClientsEvent.DUAL_AP_BOTH_INSTANCES_UP 3901 : SoftApConnectedClientsEvent.SOFT_AP_UP; 3902 3903 for (int index = softApEventList.size() - 1; 3904 index >= 0 && numOfEventNeededToUpdate != 0; index--) { 3905 SoftApConnectedClientsEvent event = softApEventList.get(index); 3906 if (event != null && event.eventType == apUpEvent) { 3907 event.maxNumClientsSettingInSoftapCapability = 3908 capability.getMaxSupportedClients(); 3909 numOfEventNeededToUpdate--; 3910 } 3911 } 3912 } 3913 } 3914 3915 /** 3916 * Increment number of times the HAL crashed. 3917 */ incrementNumHalCrashes()3918 public synchronized void incrementNumHalCrashes() { 3919 mWifiLogProto.numHalCrashes++; 3920 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3921 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__HAL_CRASH); 3922 } 3923 3924 /** 3925 * Increment number of times the Wificond crashed. 3926 */ incrementNumWificondCrashes()3927 public synchronized void incrementNumWificondCrashes() { 3928 mWifiLogProto.numWificondCrashes++; 3929 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3930 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__WIFICOND_CRASH); 3931 } 3932 3933 /** 3934 * Increment number of times the supplicant crashed. 3935 */ incrementNumSupplicantCrashes()3936 public synchronized void incrementNumSupplicantCrashes() { 3937 mWifiLogProto.numSupplicantCrashes++; 3938 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3939 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__SUPPLICANT_CRASH); 3940 } 3941 3942 /** 3943 * Increment number of times the hostapd crashed. 3944 */ incrementNumHostapdCrashes()3945 public synchronized void incrementNumHostapdCrashes() { 3946 mWifiLogProto.numHostapdCrashes++; 3947 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3948 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__HOSTAPD_CRASH); 3949 } 3950 3951 /** 3952 * Increment number of times the wifi on failed due to an error in HAL. 3953 */ incrementNumSetupClientInterfaceFailureDueToHal()3954 public synchronized void incrementNumSetupClientInterfaceFailureDueToHal() { 3955 mWifiLogProto.numSetupClientInterfaceFailureDueToHal++; 3956 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3957 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__CLIENT_FAILURE_HAL); 3958 } 3959 3960 /** 3961 * Increment number of times the wifi on failed due to an error in wificond. 3962 */ incrementNumSetupClientInterfaceFailureDueToWificond()3963 public synchronized void incrementNumSetupClientInterfaceFailureDueToWificond() { 3964 mWifiLogProto.numSetupClientInterfaceFailureDueToWificond++; 3965 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3966 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__CLIENT_FAILURE_WIFICOND); 3967 } 3968 3969 /** 3970 * Increment number of times the wifi on failed due to an error in supplicant. 3971 */ incrementNumSetupClientInterfaceFailureDueToSupplicant()3972 public synchronized void incrementNumSetupClientInterfaceFailureDueToSupplicant() { 3973 mWifiLogProto.numSetupClientInterfaceFailureDueToSupplicant++; 3974 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3975 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__CLIENT_FAILURE_SUPPLICANT); 3976 } 3977 3978 /** 3979 * Increment number of times the SoftAp on failed due to an error in HAL. 3980 */ incrementNumSetupSoftApInterfaceFailureDueToHal()3981 public synchronized void incrementNumSetupSoftApInterfaceFailureDueToHal() { 3982 mWifiLogProto.numSetupSoftApInterfaceFailureDueToHal++; 3983 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3984 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__SOFT_AP_FAILURE_HAL); 3985 } 3986 3987 /** 3988 * Increment number of times the SoftAp on failed due to an error in wificond. 3989 */ incrementNumSetupSoftApInterfaceFailureDueToWificond()3990 public synchronized void incrementNumSetupSoftApInterfaceFailureDueToWificond() { 3991 mWifiLogProto.numSetupSoftApInterfaceFailureDueToWificond++; 3992 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 3993 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__SOFT_AP_FAILURE_WIFICOND); 3994 } 3995 3996 /** 3997 * Increment number of times the SoftAp on failed due to an error in hostapd. 3998 */ incrementNumSetupSoftApInterfaceFailureDueToHostapd()3999 public synchronized void incrementNumSetupSoftApInterfaceFailureDueToHostapd() { 4000 mWifiLogProto.numSetupSoftApInterfaceFailureDueToHostapd++; 4001 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 4002 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__SOFT_AP_FAILURE_HOSTAPD); 4003 } 4004 4005 /** 4006 * Increment number of times the P2p on failed due to an error in HAL. 4007 */ incrementNumSetupP2pInterfaceFailureDueToHal()4008 public synchronized void incrementNumSetupP2pInterfaceFailureDueToHal() { 4009 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 4010 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__P2P_FAILURE_HAL); 4011 } 4012 4013 /** 4014 * Increment number of times the P2p on failed due to an error in supplicant. 4015 */ incrementNumSetupP2pInterfaceFailureDueToSupplicant()4016 public synchronized void incrementNumSetupP2pInterfaceFailureDueToSupplicant() { 4017 WifiStatsLog.write(WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED, 4018 WifiStatsLog.WIFI_SETUP_FAILURE_CRASH_REPORTED__TYPE__P2P_FAILURE_SUPPLICANT); 4019 } 4020 4021 /** 4022 * Increment number of times we got client interface down. 4023 */ incrementNumClientInterfaceDown()4024 public void incrementNumClientInterfaceDown() { 4025 synchronized (mLock) { 4026 mWifiLogProto.numClientInterfaceDown++; 4027 } 4028 } 4029 4030 /** 4031 * Increment number of times we got client interface down. 4032 */ incrementNumSoftApInterfaceDown()4033 public void incrementNumSoftApInterfaceDown() { 4034 synchronized (mLock) { 4035 mWifiLogProto.numSoftApInterfaceDown++; 4036 } 4037 } 4038 4039 /** 4040 * Increment number of times Passpoint provider being installed. 4041 */ incrementNumPasspointProviderInstallation()4042 public void incrementNumPasspointProviderInstallation() { 4043 synchronized (mLock) { 4044 mWifiLogProto.numPasspointProviderInstallation++; 4045 } 4046 } 4047 4048 /** 4049 * Increment number of times Passpoint provider is installed successfully. 4050 */ incrementNumPasspointProviderInstallSuccess()4051 public void incrementNumPasspointProviderInstallSuccess() { 4052 synchronized (mLock) { 4053 mWifiLogProto.numPasspointProviderInstallSuccess++; 4054 } 4055 } 4056 4057 /** 4058 * Increment number of times Passpoint provider being uninstalled. 4059 */ incrementNumPasspointProviderUninstallation()4060 public void incrementNumPasspointProviderUninstallation() { 4061 synchronized (mLock) { 4062 mWifiLogProto.numPasspointProviderUninstallation++; 4063 } 4064 } 4065 4066 /** 4067 * Increment number of times Passpoint provider is uninstalled successfully. 4068 */ incrementNumPasspointProviderUninstallSuccess()4069 public void incrementNumPasspointProviderUninstallSuccess() { 4070 synchronized (mLock) { 4071 mWifiLogProto.numPasspointProviderUninstallSuccess++; 4072 } 4073 } 4074 4075 /** 4076 * Increment number of Passpoint providers with no Root CA in their profile. 4077 */ incrementNumPasspointProviderWithNoRootCa()4078 public void incrementNumPasspointProviderWithNoRootCa() { 4079 synchronized (mLock) { 4080 mWifiLogProto.numPasspointProviderWithNoRootCa++; 4081 } 4082 } 4083 4084 /** 4085 * Increment number of Passpoint providers with a self-signed Root CA in their profile. 4086 */ incrementNumPasspointProviderWithSelfSignedRootCa()4087 public void incrementNumPasspointProviderWithSelfSignedRootCa() { 4088 synchronized (mLock) { 4089 mWifiLogProto.numPasspointProviderWithSelfSignedRootCa++; 4090 } 4091 } 4092 4093 /** 4094 * Increment number of Passpoint providers with subscription expiration date in their profile. 4095 */ incrementNumPasspointProviderWithSubscriptionExpiration()4096 public void incrementNumPasspointProviderWithSubscriptionExpiration() { 4097 synchronized (mLock) { 4098 mWifiLogProto.numPasspointProviderWithSubscriptionExpiration++; 4099 } 4100 } 4101 4102 /** 4103 * Increment number of times we detected a radio mode change to MCC. 4104 */ incrementNumRadioModeChangeToMcc()4105 public void incrementNumRadioModeChangeToMcc() { 4106 synchronized (mLock) { 4107 mWifiLogProto.numRadioModeChangeToMcc++; 4108 } 4109 } 4110 4111 /** 4112 * Increment number of times we detected a radio mode change to SCC. 4113 */ incrementNumRadioModeChangeToScc()4114 public void incrementNumRadioModeChangeToScc() { 4115 synchronized (mLock) { 4116 mWifiLogProto.numRadioModeChangeToScc++; 4117 } 4118 } 4119 4120 /** 4121 * Increment number of times we detected a radio mode change to SBS. 4122 */ incrementNumRadioModeChangeToSbs()4123 public void incrementNumRadioModeChangeToSbs() { 4124 synchronized (mLock) { 4125 mWifiLogProto.numRadioModeChangeToSbs++; 4126 } 4127 } 4128 4129 /** 4130 * Increment number of times we detected a radio mode change to DBS. 4131 */ incrementNumRadioModeChangeToDbs()4132 public void incrementNumRadioModeChangeToDbs() { 4133 synchronized (mLock) { 4134 mWifiLogProto.numRadioModeChangeToDbs++; 4135 } 4136 } 4137 4138 /** 4139 * Increment number of times we detected a channel did not satisfy user band preference. 4140 */ incrementNumSoftApUserBandPreferenceUnsatisfied()4141 public void incrementNumSoftApUserBandPreferenceUnsatisfied() { 4142 synchronized (mLock) { 4143 mWifiLogProto.numSoftApUserBandPreferenceUnsatisfied++; 4144 } 4145 } 4146 4147 /** 4148 * Increment N-Way network selection decision histograms: 4149 * Counts the size of various sets of scanDetails within a scan, and increment the occurrence 4150 * of that size for the associated histogram. There are ten histograms generated for each 4151 * combination of: {SSID, BSSID} *{Total, Saved, Open, Saved_or_Open, Passpoint} 4152 * Only performs this count if isFullBand is true, otherwise, increments the partial scan count 4153 */ incrementAvailableNetworksHistograms(List<ScanDetail> scanDetails, boolean isFullBand)4154 public void incrementAvailableNetworksHistograms(List<ScanDetail> scanDetails, 4155 boolean isFullBand) { 4156 synchronized (mLock) { 4157 if (mWifiConfigManager == null || mWifiNetworkSelector == null 4158 || mPasspointManager == null) { 4159 return; 4160 } 4161 if (!isFullBand) { 4162 mWifiLogProto.partialAllSingleScanListenerResults++; 4163 return; 4164 } 4165 4166 Set<ScanResultMatchInfo> ssids = new HashSet<ScanResultMatchInfo>(); 4167 int bssids = 0; 4168 Set<ScanResultMatchInfo> openSsids = new HashSet<ScanResultMatchInfo>(); 4169 int openBssids = 0; 4170 Set<ScanResultMatchInfo> savedSsids = new HashSet<ScanResultMatchInfo>(); 4171 int savedBssids = 0; 4172 // openOrSavedSsids calculated from union of savedSsids & openSsids 4173 int openOrSavedBssids = 0; 4174 Set<PasspointProvider> savedPasspointProviderProfiles = 4175 new HashSet<PasspointProvider>(); 4176 int savedPasspointProviderBssids = 0; 4177 int passpointR1Aps = 0; 4178 int passpointR2Aps = 0; 4179 int passpointR3Aps = 0; 4180 Map<ANQPNetworkKey, Integer> passpointR1UniqueEss = new HashMap<>(); 4181 Map<ANQPNetworkKey, Integer> passpointR2UniqueEss = new HashMap<>(); 4182 Map<ANQPNetworkKey, Integer> passpointR3UniqueEss = new HashMap<>(); 4183 int supporting80211mcAps = 0; 4184 for (ScanDetail scanDetail : scanDetails) { 4185 NetworkDetail networkDetail = scanDetail.getNetworkDetail(); 4186 ScanResult scanResult = scanDetail.getScanResult(); 4187 4188 // statistics to be collected for ALL APs (irrespective of signal power) 4189 if (networkDetail.is80211McResponderSupport()) { 4190 supporting80211mcAps++; 4191 } 4192 4193 ScanResultMatchInfo matchInfo = ScanResultMatchInfo.fromScanResult(scanResult); 4194 List<Pair<PasspointProvider, PasspointMatch>> matchedProviders = null; 4195 if (networkDetail.isInterworking()) { 4196 // Try to match provider, but do not allow new ANQP messages. Use cached data. 4197 matchedProviders = mPasspointManager.matchProvider(scanResult, false); 4198 if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R1) { 4199 passpointR1Aps++; 4200 } else if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R2) { 4201 passpointR2Aps++; 4202 } else if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R3) { 4203 passpointR3Aps++; 4204 } 4205 4206 long bssid = 0; 4207 boolean validBssid = false; 4208 try { 4209 bssid = Utils.parseMac(scanResult.BSSID); 4210 validBssid = true; 4211 } catch (IllegalArgumentException e) { 4212 Log.e(TAG, 4213 "Invalid BSSID provided in the scan result: " + scanResult.BSSID); 4214 } 4215 if (validBssid) { 4216 ANQPNetworkKey uniqueEss = ANQPNetworkKey.buildKey(scanResult.SSID, bssid, 4217 scanResult.hessid, networkDetail.getAnqpDomainID()); 4218 if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R1) { 4219 Integer countObj = passpointR1UniqueEss.get(uniqueEss); 4220 int count = countObj == null ? 0 : countObj; 4221 passpointR1UniqueEss.put(uniqueEss, count + 1); 4222 } else if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R2) { 4223 Integer countObj = passpointR2UniqueEss.get(uniqueEss); 4224 int count = countObj == null ? 0 : countObj; 4225 passpointR2UniqueEss.put(uniqueEss, count + 1); 4226 } else if (networkDetail.getHSRelease() == NetworkDetail.HSRelease.R3) { 4227 Integer countObj = passpointR3UniqueEss.get(uniqueEss); 4228 int count = countObj == null ? 0 : countObj; 4229 passpointR3UniqueEss.put(uniqueEss, count + 1); 4230 } 4231 } 4232 } 4233 4234 if (mWifiNetworkSelector.isSignalTooWeak(scanResult)) { 4235 continue; 4236 } 4237 4238 // statistics to be collected ONLY for those APs with sufficient signal power 4239 4240 ssids.add(matchInfo); 4241 bssids++; 4242 boolean isOpen = ScanResultUtil.isScanResultForOpenNetwork(scanResult) 4243 || ScanResultUtil.isScanResultForOweNetwork(scanResult); 4244 WifiConfiguration config = 4245 mWifiConfigManager.getSavedNetworkForScanDetail(scanDetail); 4246 boolean isSaved = (config != null) && !config.isEphemeral() 4247 && !config.isPasspoint(); 4248 if (isOpen) { 4249 openSsids.add(matchInfo); 4250 openBssids++; 4251 } 4252 if (isSaved) { 4253 savedSsids.add(matchInfo); 4254 savedBssids++; 4255 } 4256 if (isOpen || isSaved) { 4257 openOrSavedBssids++; 4258 // Calculate openOrSavedSsids union later 4259 } 4260 if (matchedProviders != null && !matchedProviders.isEmpty()) { 4261 for (Pair<PasspointProvider, PasspointMatch> passpointProvider : 4262 matchedProviders) { 4263 savedPasspointProviderProfiles.add(passpointProvider.first); 4264 } 4265 savedPasspointProviderBssids++; 4266 } 4267 } 4268 mWifiLogProto.fullBandAllSingleScanListenerResults++; 4269 incrementTotalScanSsids(mTotalSsidsInScanHistogram, ssids.size()); 4270 incrementTotalScanResults(mTotalBssidsInScanHistogram, bssids); 4271 incrementSsid(mAvailableOpenSsidsInScanHistogram, openSsids.size()); 4272 incrementBssid(mAvailableOpenBssidsInScanHistogram, openBssids); 4273 incrementSsid(mAvailableSavedSsidsInScanHistogram, savedSsids.size()); 4274 incrementBssid(mAvailableSavedBssidsInScanHistogram, savedBssids); 4275 openSsids.addAll(savedSsids); // openSsids = Union(openSsids, savedSsids) 4276 incrementSsid(mAvailableOpenOrSavedSsidsInScanHistogram, openSsids.size()); 4277 incrementBssid(mAvailableOpenOrSavedBssidsInScanHistogram, openOrSavedBssids); 4278 incrementSsid(mAvailableSavedPasspointProviderProfilesInScanHistogram, 4279 savedPasspointProviderProfiles.size()); 4280 incrementBssid(mAvailableSavedPasspointProviderBssidsInScanHistogram, 4281 savedPasspointProviderBssids); 4282 incrementTotalPasspointAps(mObservedHotspotR1ApInScanHistogram, passpointR1Aps); 4283 incrementTotalPasspointAps(mObservedHotspotR2ApInScanHistogram, passpointR2Aps); 4284 incrementTotalPasspointAps(mObservedHotspotR3ApInScanHistogram, passpointR3Aps); 4285 incrementTotalUniquePasspointEss(mObservedHotspotR1EssInScanHistogram, 4286 passpointR1UniqueEss.size()); 4287 incrementTotalUniquePasspointEss(mObservedHotspotR2EssInScanHistogram, 4288 passpointR2UniqueEss.size()); 4289 incrementTotalUniquePasspointEss(mObservedHotspotR3EssInScanHistogram, 4290 passpointR3UniqueEss.size()); 4291 for (Integer count : passpointR1UniqueEss.values()) { 4292 incrementPasspointPerUniqueEss(mObservedHotspotR1ApsPerEssInScanHistogram, count); 4293 } 4294 for (Integer count : passpointR2UniqueEss.values()) { 4295 incrementPasspointPerUniqueEss(mObservedHotspotR2ApsPerEssInScanHistogram, count); 4296 } 4297 for (Integer count : passpointR3UniqueEss.values()) { 4298 incrementPasspointPerUniqueEss(mObservedHotspotR3ApsPerEssInScanHistogram, count); 4299 } 4300 increment80211mcAps(mObserved80211mcApInScanHistogram, supporting80211mcAps); 4301 } 4302 } 4303 4304 /** Increments the occurence of a "Connect to Network" notification. */ incrementConnectToNetworkNotification(String notifierTag, int notificationType)4305 public void incrementConnectToNetworkNotification(String notifierTag, int notificationType) { 4306 synchronized (mLock) { 4307 int count = mConnectToNetworkNotificationCount.get(notificationType); 4308 mConnectToNetworkNotificationCount.put(notificationType, count + 1); 4309 } 4310 } 4311 4312 /** Increments the occurence of an "Connect to Network" notification user action. */ incrementConnectToNetworkNotificationAction(String notifierTag, int notificationType, int actionType)4313 public void incrementConnectToNetworkNotificationAction(String notifierTag, 4314 int notificationType, int actionType) { 4315 synchronized (mLock) { 4316 int key = notificationType * CONNECT_TO_NETWORK_NOTIFICATION_ACTION_KEY_MULTIPLIER 4317 + actionType; 4318 int count = mConnectToNetworkNotificationActionCount.get(key); 4319 mConnectToNetworkNotificationActionCount.put(key, count + 1); 4320 } 4321 } 4322 4323 /** 4324 * Sets the number of SSIDs blocklisted from recommendation by the open network notification 4325 * recommender. 4326 */ setNetworkRecommenderBlocklistSize(String notifierTag, int size)4327 public void setNetworkRecommenderBlocklistSize(String notifierTag, int size) { 4328 synchronized (mLock) { 4329 mOpenNetworkRecommenderBlocklistSize = size; 4330 } 4331 } 4332 4333 /** Sets if the available network notification feature is enabled. */ setIsWifiNetworksAvailableNotificationEnabled(String notifierTag, boolean enabled)4334 public void setIsWifiNetworksAvailableNotificationEnabled(String notifierTag, boolean enabled) { 4335 synchronized (mLock) { 4336 mIsWifiNetworksAvailableNotificationOn = enabled; 4337 } 4338 } 4339 4340 /** Increments the occurence of connection attempts that were initiated unsuccessfully */ incrementNumNetworkRecommendationUpdates(String notifierTag)4341 public void incrementNumNetworkRecommendationUpdates(String notifierTag) { 4342 synchronized (mLock) { 4343 mNumOpenNetworkRecommendationUpdates++; 4344 } 4345 } 4346 4347 /** Increments the occurence of connection attempts that were initiated unsuccessfully */ incrementNumNetworkConnectMessageFailedToSend(String notifierTag)4348 public void incrementNumNetworkConnectMessageFailedToSend(String notifierTag) { 4349 synchronized (mLock) { 4350 mNumOpenNetworkConnectMessageFailedToSend++; 4351 } 4352 } 4353 4354 /** Log firmware alert related metrics */ logFirmwareAlert(String ifaceName, int errorCode)4355 public void logFirmwareAlert(String ifaceName, int errorCode) { 4356 incrementAlertReasonCount(errorCode); 4357 logWifiIsUnusableEvent(ifaceName, WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT, errorCode); 4358 addToWifiUsabilityStatsList(ifaceName, WifiUsabilityStats.LABEL_BAD, 4359 WifiUsabilityStats.TYPE_FIRMWARE_ALERT, errorCode); 4360 } 4361 4362 public static final String PROTO_DUMP_ARG = "wifiMetricsProto"; 4363 public static final String CLEAN_DUMP_ARG = "clean"; 4364 4365 /** 4366 * Dump all WifiMetrics. Collects some metrics from ConfigStore, Settings and WifiManager 4367 * at this time. 4368 * 4369 * @param fd unused 4370 * @param pw PrintWriter for writing dump to 4371 * @param args [wifiMetricsProto [clean]] 4372 */ dump(FileDescriptor fd, PrintWriter pw, String[] args)4373 public void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 4374 synchronized (mLock) { 4375 consolidateScoringParams(); 4376 if (args != null && args.length > 0 && PROTO_DUMP_ARG.equals(args[0])) { 4377 // Dump serialized WifiLog proto 4378 consolidateProto(); 4379 byte[] wifiMetricsProto = WifiMetricsProto.WifiLog.toByteArray(mWifiLogProto); 4380 String metricsProtoDump = Base64.encodeToString(wifiMetricsProto, Base64.DEFAULT); 4381 if (args.length > 1 && CLEAN_DUMP_ARG.equals(args[1])) { 4382 // Output metrics proto bytes (base64) and nothing else 4383 pw.print(metricsProtoDump); 4384 } else { 4385 // Tag the start and end of the metrics proto bytes 4386 pw.println("WifiMetrics:"); 4387 pw.println(metricsProtoDump); 4388 pw.println("EndWifiMetrics"); 4389 } 4390 clear(); 4391 } else { 4392 pw.println("WifiMetrics:"); 4393 pw.println("mConnectionEvents:"); 4394 for (ConnectionEvent event : mConnectionEventList) { 4395 String eventLine = event.toString(); 4396 if (mCurrentConnectionEventPerIface.containsValue(event)) { 4397 eventLine += " CURRENTLY OPEN EVENT"; 4398 } 4399 pw.println(eventLine); 4400 } 4401 pw.println("mWifiLogProto.numSavedNetworks=" + mWifiLogProto.numSavedNetworks); 4402 pw.println("mWifiLogProto.numSavedNetworksWithMacRandomization=" 4403 + mWifiLogProto.numSavedNetworksWithMacRandomization); 4404 pw.println("mWifiLogProto.numOpenNetworks=" + mWifiLogProto.numOpenNetworks); 4405 pw.println("mWifiLogProto.numLegacyPersonalNetworks=" 4406 + mWifiLogProto.numLegacyPersonalNetworks); 4407 pw.println("mWifiLogProto.numLegacyEnterpriseNetworks=" 4408 + mWifiLogProto.numLegacyEnterpriseNetworks); 4409 pw.println("mWifiLogProto.numEnhancedOpenNetworks=" 4410 + mWifiLogProto.numEnhancedOpenNetworks); 4411 pw.println("mWifiLogProto.numWpa3PersonalNetworks=" 4412 + mWifiLogProto.numWpa3PersonalNetworks); 4413 pw.println("mWifiLogProto.numWpa3EnterpriseNetworks=" 4414 + mWifiLogProto.numWpa3EnterpriseNetworks); 4415 pw.println("mWifiLogProto.numWapiPersonalNetworks=" 4416 + mWifiLogProto.numWapiPersonalNetworks); 4417 pw.println("mWifiLogProto.numWapiEnterpriseNetworks=" 4418 + mWifiLogProto.numWapiEnterpriseNetworks); 4419 pw.println("mWifiLogProto.numHiddenNetworks=" + mWifiLogProto.numHiddenNetworks); 4420 pw.println("mWifiLogProto.numPasspointNetworks=" 4421 + mWifiLogProto.numPasspointNetworks); 4422 pw.println("mWifiLogProto.isLocationEnabled=" + mWifiLogProto.isLocationEnabled); 4423 pw.println("mWifiLogProto.isScanningAlwaysEnabled=" 4424 + mWifiLogProto.isScanningAlwaysEnabled); 4425 pw.println("mWifiLogProto.isVerboseLoggingEnabled=" 4426 + mWifiLogProto.isVerboseLoggingEnabled); 4427 pw.println("mWifiLogProto.isEnhancedMacRandomizationForceEnabled=" 4428 + mWifiLogProto.isEnhancedMacRandomizationForceEnabled); 4429 pw.println("mWifiLogProto.isWifiWakeEnabled=" + mWifiLogProto.isWifiWakeEnabled); 4430 pw.println("mWifiLogProto.numNetworksAddedByUser=" 4431 + mWifiLogProto.numNetworksAddedByUser); 4432 pw.println("mWifiLogProto.numNetworksAddedByApps=" 4433 + mWifiLogProto.numNetworksAddedByApps); 4434 pw.println("mWifiLogProto.numNonEmptyScanResults=" 4435 + mWifiLogProto.numNonEmptyScanResults); 4436 pw.println("mWifiLogProto.numEmptyScanResults=" 4437 + mWifiLogProto.numEmptyScanResults); 4438 pw.println("mWifiLogProto.numConnecitvityOneshotScans=" 4439 + mWifiLogProto.numConnectivityOneshotScans); 4440 pw.println("mWifiLogProto.numOneshotScans=" 4441 + mWifiLogProto.numOneshotScans); 4442 pw.println("mWifiLogProto.numOneshotHasDfsChannelScans=" 4443 + mWifiLogProto.numOneshotHasDfsChannelScans); 4444 pw.println("mWifiLogProto.numBackgroundScans=" 4445 + mWifiLogProto.numBackgroundScans); 4446 pw.println("mWifiLogProto.numExternalAppOneshotScanRequests=" 4447 + mWifiLogProto.numExternalAppOneshotScanRequests); 4448 pw.println("mWifiLogProto.numExternalForegroundAppOneshotScanRequestsThrottled=" 4449 + mWifiLogProto.numExternalForegroundAppOneshotScanRequestsThrottled); 4450 pw.println("mWifiLogProto.numExternalBackgroundAppOneshotScanRequestsThrottled=" 4451 + mWifiLogProto.numExternalBackgroundAppOneshotScanRequestsThrottled); 4452 pw.println("mWifiLogProto.meteredNetworkStatsSaved="); 4453 pw.println(mMeteredNetworkStatsBuilder.toProto(false)); 4454 pw.println("mWifiLogProto.meteredNetworkStatsSuggestion="); 4455 pw.println(mMeteredNetworkStatsBuilder.toProto(true)); 4456 pw.println("mScanReturnEntries:"); 4457 pw.println(" SCAN_UNKNOWN: " + getScanReturnEntry( 4458 WifiMetricsProto.WifiLog.SCAN_UNKNOWN)); 4459 pw.println(" SCAN_SUCCESS: " + getScanReturnEntry( 4460 WifiMetricsProto.WifiLog.SCAN_SUCCESS)); 4461 pw.println(" SCAN_FAILURE_INTERRUPTED: " + getScanReturnEntry( 4462 WifiMetricsProto.WifiLog.SCAN_FAILURE_INTERRUPTED)); 4463 pw.println(" SCAN_FAILURE_INVALID_CONFIGURATION: " + getScanReturnEntry( 4464 WifiMetricsProto.WifiLog.SCAN_FAILURE_INVALID_CONFIGURATION)); 4465 pw.println(" FAILURE_WIFI_DISABLED: " + getScanReturnEntry( 4466 WifiMetricsProto.WifiLog.FAILURE_WIFI_DISABLED)); 4467 4468 pw.println("mSystemStateEntries: <state><screenOn> : <scansInitiated>"); 4469 pw.println(" WIFI_UNKNOWN ON: " 4470 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_UNKNOWN, true)); 4471 pw.println(" WIFI_DISABLED ON: " 4472 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_DISABLED, true)); 4473 pw.println(" WIFI_DISCONNECTED ON: " 4474 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_DISCONNECTED, true)); 4475 pw.println(" WIFI_ASSOCIATED ON: " 4476 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED, true)); 4477 pw.println(" WIFI_UNKNOWN OFF: " 4478 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_UNKNOWN, false)); 4479 pw.println(" WIFI_DISABLED OFF: " 4480 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_DISABLED, false)); 4481 pw.println(" WIFI_DISCONNECTED OFF: " 4482 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_DISCONNECTED, false)); 4483 pw.println(" WIFI_ASSOCIATED OFF: " 4484 + getSystemStateCount(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED, false)); 4485 pw.println("mWifiLogProto.numConnectivityWatchdogPnoGood=" 4486 + mWifiLogProto.numConnectivityWatchdogPnoGood); 4487 pw.println("mWifiLogProto.numConnectivityWatchdogPnoBad=" 4488 + mWifiLogProto.numConnectivityWatchdogPnoBad); 4489 pw.println("mWifiLogProto.numConnectivityWatchdogBackgroundGood=" 4490 + mWifiLogProto.numConnectivityWatchdogBackgroundGood); 4491 pw.println("mWifiLogProto.numConnectivityWatchdogBackgroundBad=" 4492 + mWifiLogProto.numConnectivityWatchdogBackgroundBad); 4493 pw.println("mWifiLogProto.numLastResortWatchdogTriggers=" 4494 + mWifiLogProto.numLastResortWatchdogTriggers); 4495 pw.println("mWifiLogProto.numLastResortWatchdogBadAssociationNetworksTotal=" 4496 + mWifiLogProto.numLastResortWatchdogBadAssociationNetworksTotal); 4497 pw.println("mWifiLogProto.numLastResortWatchdogBadAuthenticationNetworksTotal=" 4498 + mWifiLogProto.numLastResortWatchdogBadAuthenticationNetworksTotal); 4499 pw.println("mWifiLogProto.numLastResortWatchdogBadDhcpNetworksTotal=" 4500 + mWifiLogProto.numLastResortWatchdogBadDhcpNetworksTotal); 4501 pw.println("mWifiLogProto.numLastResortWatchdogBadOtherNetworksTotal=" 4502 + mWifiLogProto.numLastResortWatchdogBadOtherNetworksTotal); 4503 pw.println("mWifiLogProto.numLastResortWatchdogAvailableNetworksTotal=" 4504 + mWifiLogProto.numLastResortWatchdogAvailableNetworksTotal); 4505 pw.println("mWifiLogProto.numLastResortWatchdogTriggersWithBadAssociation=" 4506 + mWifiLogProto.numLastResortWatchdogTriggersWithBadAssociation); 4507 pw.println("mWifiLogProto.numLastResortWatchdogTriggersWithBadAuthentication=" 4508 + mWifiLogProto.numLastResortWatchdogTriggersWithBadAuthentication); 4509 pw.println("mWifiLogProto.numLastResortWatchdogTriggersWithBadDhcp=" 4510 + mWifiLogProto.numLastResortWatchdogTriggersWithBadDhcp); 4511 pw.println("mWifiLogProto.numLastResortWatchdogTriggersWithBadOther=" 4512 + mWifiLogProto.numLastResortWatchdogTriggersWithBadOther); 4513 pw.println("mWifiLogProto.numLastResortWatchdogSuccesses=" 4514 + mWifiLogProto.numLastResortWatchdogSuccesses); 4515 pw.println("mWifiLogProto.watchdogTotalConnectionFailureCountAfterTrigger=" 4516 + mWifiLogProto.watchdogTotalConnectionFailureCountAfterTrigger); 4517 pw.println("mWifiLogProto.watchdogTriggerToConnectionSuccessDurationMs=" 4518 + mWifiLogProto.watchdogTriggerToConnectionSuccessDurationMs); 4519 pw.println("mWifiLogProto.recordDurationSec=" 4520 + ((mClock.getElapsedSinceBootMillis() / 1000) - mRecordStartTimeSec)); 4521 4522 try { 4523 JSONObject rssiMap = new JSONObject(); 4524 for (Map.Entry<Integer, SparseIntArray> entry : mRssiPollCountsMap.entrySet()) { 4525 int frequency = entry.getKey(); 4526 final SparseIntArray histogram = entry.getValue(); 4527 JSONArray histogramElements = new JSONArray(); 4528 for (int i = MIN_RSSI_POLL; i <= MAX_RSSI_POLL; i++) { 4529 int count = histogram.get(i); 4530 if (count == 0) { 4531 continue; 4532 } 4533 JSONObject histogramElement = new JSONObject(); 4534 histogramElement.put(Integer.toString(i), count); 4535 histogramElements.put(histogramElement); 4536 } 4537 rssiMap.put(Integer.toString(frequency), histogramElements); 4538 } 4539 pw.println("mWifiLogProto.rssiPollCount: " + rssiMap.toString()); 4540 } catch (JSONException e) { 4541 pw.println("JSONException occurred: " + e.getMessage()); 4542 } 4543 4544 pw.println("mWifiLogProto.rssiPollDeltaCount: Printing counts for [" 4545 + MIN_RSSI_DELTA + ", " + MAX_RSSI_DELTA + "]"); 4546 StringBuilder sb = new StringBuilder(); 4547 for (int i = MIN_RSSI_DELTA; i <= MAX_RSSI_DELTA; i++) { 4548 sb.append(mRssiDeltaCounts.get(i) + " "); 4549 } 4550 pw.println(" " + sb.toString()); 4551 pw.println("mWifiLogProto.linkSpeedCounts: "); 4552 sb.setLength(0); 4553 for (int i = 0; i < mLinkSpeedCounts.size(); i++) { 4554 LinkSpeedCount linkSpeedCount = mLinkSpeedCounts.valueAt(i); 4555 sb.append(linkSpeedCount.linkSpeedMbps).append(":{") 4556 .append(linkSpeedCount.count).append(", ") 4557 .append(linkSpeedCount.rssiSumDbm).append(", ") 4558 .append(linkSpeedCount.rssiSumOfSquaresDbmSq).append("} "); 4559 } 4560 if (sb.length() > 0) { 4561 pw.println(sb.toString()); 4562 } 4563 pw.print("mWifiLogProto.alertReasonCounts="); 4564 sb.setLength(0); 4565 for (int i = WifiLoggerHal.WIFI_ALERT_REASON_MIN; 4566 i <= WifiLoggerHal.WIFI_ALERT_REASON_MAX; i++) { 4567 int count = mWifiAlertReasonCounts.get(i); 4568 if (count > 0) { 4569 sb.append("(" + i + "," + count + "),"); 4570 } 4571 } 4572 if (sb.length() > 1) { 4573 sb.setLength(sb.length() - 1); // strip trailing comma 4574 pw.println(sb.toString()); 4575 } else { 4576 pw.println("()"); 4577 } 4578 pw.println("mWifiLogProto.numTotalScanResults=" 4579 + mWifiLogProto.numTotalScanResults); 4580 pw.println("mWifiLogProto.numOpenNetworkScanResults=" 4581 + mWifiLogProto.numOpenNetworkScanResults); 4582 pw.println("mWifiLogProto.numLegacyPersonalNetworkScanResults=" 4583 + mWifiLogProto.numLegacyPersonalNetworkScanResults); 4584 pw.println("mWifiLogProto.numLegacyEnterpriseNetworkScanResults=" 4585 + mWifiLogProto.numLegacyEnterpriseNetworkScanResults); 4586 pw.println("mWifiLogProto.numEnhancedOpenNetworkScanResults=" 4587 + mWifiLogProto.numEnhancedOpenNetworkScanResults); 4588 pw.println("mWifiLogProto.numWpa3PersonalNetworkScanResults=" 4589 + mWifiLogProto.numWpa3PersonalNetworkScanResults); 4590 pw.println("mWifiLogProto.numWpa3EnterpriseNetworkScanResults=" 4591 + mWifiLogProto.numWpa3EnterpriseNetworkScanResults); 4592 pw.println("mWifiLogProto.numWapiPersonalNetworkScanResults=" 4593 + mWifiLogProto.numWapiPersonalNetworkScanResults); 4594 pw.println("mWifiLogProto.numWapiEnterpriseNetworkScanResults=" 4595 + mWifiLogProto.numWapiEnterpriseNetworkScanResults); 4596 pw.println("mWifiLogProto.numHiddenNetworkScanResults=" 4597 + mWifiLogProto.numHiddenNetworkScanResults); 4598 pw.println("mWifiLogProto.numHotspot2R1NetworkScanResults=" 4599 + mWifiLogProto.numHotspot2R1NetworkScanResults); 4600 pw.println("mWifiLogProto.numHotspot2R2NetworkScanResults=" 4601 + mWifiLogProto.numHotspot2R2NetworkScanResults); 4602 pw.println("mWifiLogProto.numHotspot2R3NetworkScanResults=" 4603 + mWifiLogProto.numHotspot2R3NetworkScanResults); 4604 pw.println("mWifiLogProto.numMboSupportedNetworkScanResults=" 4605 + mWifiLogProto.numMboSupportedNetworkScanResults); 4606 pw.println("mWifiLogProto.numMboCellularDataAwareNetworkScanResults=" 4607 + mWifiLogProto.numMboCellularDataAwareNetworkScanResults); 4608 pw.println("mWifiLogProto.numOceSupportedNetworkScanResults=" 4609 + mWifiLogProto.numOceSupportedNetworkScanResults); 4610 pw.println("mWifiLogProto.numFilsSupportedNetworkScanResults=" 4611 + mWifiLogProto.numFilsSupportedNetworkScanResults); 4612 pw.println("mWifiLogProto.num11AxNetworkScanResults=" 4613 + mWifiLogProto.num11AxNetworkScanResults); 4614 pw.println("mWifiLogProto.num6GNetworkScanResults" 4615 + mWifiLogProto.num6GNetworkScanResults); 4616 pw.println("mWifiLogProto.num6GPscNetworkScanResults" 4617 + mWifiLogProto.num6GPscNetworkScanResults); 4618 pw.println("mWifiLogProto.numBssidFilteredDueToMboAssocDisallowInd=" 4619 + mWifiLogProto.numBssidFilteredDueToMboAssocDisallowInd); 4620 pw.println("mWifiLogProto.numConnectToNetworkSupportingMbo=" 4621 + mWifiLogProto.numConnectToNetworkSupportingMbo); 4622 pw.println("mWifiLogProto.numConnectToNetworkSupportingOce=" 4623 + mWifiLogProto.numConnectToNetworkSupportingOce); 4624 pw.println("mWifiLogProto.numSteeringRequest=" 4625 + mWifiLogProto.numSteeringRequest); 4626 pw.println("mWifiLogProto.numForceScanDueToSteeringRequest=" 4627 + mWifiLogProto.numForceScanDueToSteeringRequest); 4628 pw.println("mWifiLogProto.numMboCellularSwitchRequest=" 4629 + mWifiLogProto.numMboCellularSwitchRequest); 4630 pw.println("mWifiLogProto.numSteeringRequestIncludingMboAssocRetryDelay=" 4631 + mWifiLogProto.numSteeringRequestIncludingMboAssocRetryDelay); 4632 pw.println("mWifiLogProto.numConnectRequestWithFilsAkm=" 4633 + mWifiLogProto.numConnectRequestWithFilsAkm); 4634 pw.println("mWifiLogProto.numL2ConnectionThroughFilsAuthentication=" 4635 + mWifiLogProto.numL2ConnectionThroughFilsAuthentication); 4636 pw.println("mWifiLogProto.recentFailureAssociationStatus=" 4637 + mRecentFailureAssociationStatus.toString()); 4638 4639 pw.println("mWifiLogProto.numScans=" + mWifiLogProto.numScans); 4640 pw.println("mWifiLogProto.WifiScoreCount: [" + MIN_WIFI_SCORE + ", " 4641 + MAX_WIFI_SCORE + "]"); 4642 for (int i = 0; i <= MAX_WIFI_SCORE; i++) { 4643 pw.print(mWifiScoreCounts.get(i) + " "); 4644 } 4645 pw.println(); // add a line after wifi scores 4646 pw.println("mWifiLogProto.WifiUsabilityScoreCount: [" + MIN_WIFI_USABILITY_SCORE 4647 + ", " + MAX_WIFI_USABILITY_SCORE + "]"); 4648 for (int i = MIN_WIFI_USABILITY_SCORE; i <= MAX_WIFI_USABILITY_SCORE; i++) { 4649 pw.print(mWifiUsabilityScoreCounts.get(i) + " "); 4650 } 4651 pw.println(); // add a line after wifi usability scores 4652 pw.println("mWifiLogProto.SoftApManagerReturnCodeCounts:"); 4653 pw.println(" SUCCESS: " + mSoftApManagerReturnCodeCounts.get( 4654 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_STARTED_SUCCESSFULLY)); 4655 pw.println(" FAILED_GENERAL_ERROR: " + mSoftApManagerReturnCodeCounts.get( 4656 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_GENERAL_ERROR)); 4657 pw.println(" FAILED_NO_CHANNEL: " + mSoftApManagerReturnCodeCounts.get( 4658 WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_NO_CHANNEL)); 4659 pw.println(" FAILED_UNSUPPORTED_CONFIGURATION: " 4660 + mSoftApManagerReturnCodeCounts.get( 4661 WifiMetricsProto.SoftApReturnCodeCount 4662 .SOFT_AP_FAILED_UNSUPPORTED_CONFIGURATION)); 4663 pw.print("\n"); 4664 pw.println("mWifiLogProto.numHalCrashes=" 4665 + mWifiLogProto.numHalCrashes); 4666 pw.println("mWifiLogProto.numWificondCrashes=" 4667 + mWifiLogProto.numWificondCrashes); 4668 pw.println("mWifiLogProto.numSupplicantCrashes=" 4669 + mWifiLogProto.numSupplicantCrashes); 4670 pw.println("mWifiLogProto.numHostapdCrashes=" 4671 + mWifiLogProto.numHostapdCrashes); 4672 pw.println("mWifiLogProto.numSetupClientInterfaceFailureDueToHal=" 4673 + mWifiLogProto.numSetupClientInterfaceFailureDueToHal); 4674 pw.println("mWifiLogProto.numSetupClientInterfaceFailureDueToWificond=" 4675 + mWifiLogProto.numSetupClientInterfaceFailureDueToWificond); 4676 pw.println("mWifiLogProto.numSetupClientInterfaceFailureDueToSupplicant=" 4677 + mWifiLogProto.numSetupClientInterfaceFailureDueToSupplicant); 4678 pw.println("mWifiLogProto.numSetupSoftApInterfaceFailureDueToHal=" 4679 + mWifiLogProto.numSetupSoftApInterfaceFailureDueToHal); 4680 pw.println("mWifiLogProto.numSetupSoftApInterfaceFailureDueToWificond=" 4681 + mWifiLogProto.numSetupSoftApInterfaceFailureDueToWificond); 4682 pw.println("mWifiLogProto.numSetupSoftApInterfaceFailureDueToHostapd=" 4683 + mWifiLogProto.numSetupSoftApInterfaceFailureDueToHostapd); 4684 pw.println("StaEventList:"); 4685 for (StaEventWithTime event : mStaEventList) { 4686 pw.println(event); 4687 } 4688 pw.println("UserActionEvents:"); 4689 for (UserActionEventWithTime event : mUserActionEventList) { 4690 pw.println(event); 4691 } 4692 4693 pw.println("mWifiLogProto.numPasspointProviders=" 4694 + mWifiLogProto.numPasspointProviders); 4695 pw.println("mWifiLogProto.numPasspointProviderInstallation=" 4696 + mWifiLogProto.numPasspointProviderInstallation); 4697 pw.println("mWifiLogProto.numPasspointProviderInstallSuccess=" 4698 + mWifiLogProto.numPasspointProviderInstallSuccess); 4699 pw.println("mWifiLogProto.numPasspointProviderUninstallation=" 4700 + mWifiLogProto.numPasspointProviderUninstallation); 4701 pw.println("mWifiLogProto.numPasspointProviderUninstallSuccess=" 4702 + mWifiLogProto.numPasspointProviderUninstallSuccess); 4703 pw.println("mWifiLogProto.numPasspointProvidersSuccessfullyConnected=" 4704 + mWifiLogProto.numPasspointProvidersSuccessfullyConnected); 4705 4706 pw.println("mWifiLogProto.installedPasspointProfileTypeForR1:" 4707 + mInstalledPasspointProfileTypeForR1); 4708 pw.println("mWifiLogProto.installedPasspointProfileTypeForR2:" 4709 + mInstalledPasspointProfileTypeForR2); 4710 4711 pw.println("mWifiLogProto.passpointProvisionStats.numProvisionSuccess=" 4712 + mNumProvisionSuccess); 4713 pw.println("mWifiLogProto.passpointProvisionStats.provisionFailureCount:" 4714 + mPasspointProvisionFailureCounts); 4715 pw.println("mWifiLogProto.totalNumberOfPasspointConnectionsWithVenueUrl=" 4716 + mWifiLogProto.totalNumberOfPasspointConnectionsWithVenueUrl); 4717 pw.println( 4718 "mWifiLogProto.totalNumberOfPasspointConnectionsWithTermsAndConditionsUrl=" 4719 + mWifiLogProto 4720 .totalNumberOfPasspointConnectionsWithTermsAndConditionsUrl); 4721 pw.println( 4722 "mWifiLogProto" 4723 + ".totalNumberOfPasspointAcceptanceOfTermsAndConditions=" 4724 + mWifiLogProto 4725 .totalNumberOfPasspointAcceptanceOfTermsAndConditions); 4726 pw.println("mWifiLogProto.totalNumberOfPasspointProfilesWithDecoratedIdentity=" 4727 + mWifiLogProto.totalNumberOfPasspointProfilesWithDecoratedIdentity); 4728 pw.println("mWifiLogProto.passpointDeauthImminentScope=" 4729 + mPasspointDeauthImminentScope.toString()); 4730 4731 pw.println("mWifiLogProto.numRadioModeChangeToMcc=" 4732 + mWifiLogProto.numRadioModeChangeToMcc); 4733 pw.println("mWifiLogProto.numRadioModeChangeToScc=" 4734 + mWifiLogProto.numRadioModeChangeToScc); 4735 pw.println("mWifiLogProto.numRadioModeChangeToSbs=" 4736 + mWifiLogProto.numRadioModeChangeToSbs); 4737 pw.println("mWifiLogProto.numRadioModeChangeToDbs=" 4738 + mWifiLogProto.numRadioModeChangeToDbs); 4739 pw.println("mWifiLogProto.numSoftApUserBandPreferenceUnsatisfied=" 4740 + mWifiLogProto.numSoftApUserBandPreferenceUnsatisfied); 4741 pw.println("mTotalSsidsInScanHistogram:" 4742 + mTotalSsidsInScanHistogram.toString()); 4743 pw.println("mTotalBssidsInScanHistogram:" 4744 + mTotalBssidsInScanHistogram.toString()); 4745 pw.println("mAvailableOpenSsidsInScanHistogram:" 4746 + mAvailableOpenSsidsInScanHistogram.toString()); 4747 pw.println("mAvailableOpenBssidsInScanHistogram:" 4748 + mAvailableOpenBssidsInScanHistogram.toString()); 4749 pw.println("mAvailableSavedSsidsInScanHistogram:" 4750 + mAvailableSavedSsidsInScanHistogram.toString()); 4751 pw.println("mAvailableSavedBssidsInScanHistogram:" 4752 + mAvailableSavedBssidsInScanHistogram.toString()); 4753 pw.println("mAvailableOpenOrSavedSsidsInScanHistogram:" 4754 + mAvailableOpenOrSavedSsidsInScanHistogram.toString()); 4755 pw.println("mAvailableOpenOrSavedBssidsInScanHistogram:" 4756 + mAvailableOpenOrSavedBssidsInScanHistogram.toString()); 4757 pw.println("mAvailableSavedPasspointProviderProfilesInScanHistogram:" 4758 + mAvailableSavedPasspointProviderProfilesInScanHistogram.toString()); 4759 pw.println("mAvailableSavedPasspointProviderBssidsInScanHistogram:" 4760 + mAvailableSavedPasspointProviderBssidsInScanHistogram.toString()); 4761 pw.println("mWifiLogProto.partialAllSingleScanListenerResults=" 4762 + mWifiLogProto.partialAllSingleScanListenerResults); 4763 pw.println("mWifiLogProto.fullBandAllSingleScanListenerResults=" 4764 + mWifiLogProto.fullBandAllSingleScanListenerResults); 4765 pw.println("mWifiAwareMetrics:"); 4766 mWifiAwareMetrics.dump(fd, pw, args); 4767 pw.println("mRttMetrics:"); 4768 mRttMetrics.dump(fd, pw, args); 4769 4770 pw.println("mPnoScanMetrics.numPnoScanAttempts=" 4771 + mPnoScanMetrics.numPnoScanAttempts); 4772 pw.println("mPnoScanMetrics.numPnoScanFailed=" 4773 + mPnoScanMetrics.numPnoScanFailed); 4774 pw.println("mPnoScanMetrics.numPnoScanStartedOverOffload=" 4775 + mPnoScanMetrics.numPnoScanStartedOverOffload); 4776 pw.println("mPnoScanMetrics.numPnoScanFailedOverOffload=" 4777 + mPnoScanMetrics.numPnoScanFailedOverOffload); 4778 pw.println("mPnoScanMetrics.numPnoFoundNetworkEvents=" 4779 + mPnoScanMetrics.numPnoFoundNetworkEvents); 4780 4781 pw.println("mWifiLinkLayerUsageStats.loggingDurationMs=" 4782 + mWifiLinkLayerUsageStats.loggingDurationMs); 4783 pw.println("mWifiLinkLayerUsageStats.radioOnTimeMs=" 4784 + mWifiLinkLayerUsageStats.radioOnTimeMs); 4785 pw.println("mWifiLinkLayerUsageStats.radioTxTimeMs=" 4786 + mWifiLinkLayerUsageStats.radioTxTimeMs); 4787 pw.println("mWifiLinkLayerUsageStats.radioRxTimeMs=" 4788 + mWifiLinkLayerUsageStats.radioRxTimeMs); 4789 pw.println("mWifiLinkLayerUsageStats.radioScanTimeMs=" 4790 + mWifiLinkLayerUsageStats.radioScanTimeMs); 4791 pw.println("mWifiLinkLayerUsageStats.radioNanScanTimeMs=" 4792 + mWifiLinkLayerUsageStats.radioNanScanTimeMs); 4793 pw.println("mWifiLinkLayerUsageStats.radioBackgroundScanTimeMs=" 4794 + mWifiLinkLayerUsageStats.radioBackgroundScanTimeMs); 4795 pw.println("mWifiLinkLayerUsageStats.radioRoamScanTimeMs=" 4796 + mWifiLinkLayerUsageStats.radioRoamScanTimeMs); 4797 pw.println("mWifiLinkLayerUsageStats.radioPnoScanTimeMs=" 4798 + mWifiLinkLayerUsageStats.radioPnoScanTimeMs); 4799 pw.println("mWifiLinkLayerUsageStats.radioHs20ScanTimeMs=" 4800 + mWifiLinkLayerUsageStats.radioHs20ScanTimeMs); 4801 pw.println("mWifiLinkLayerUsageStats per Radio Stats: "); 4802 for (int i = 0; i < mRadioStats.size(); i++) { 4803 RadioStats radioStat = mRadioStats.valueAt(i); 4804 pw.println("radioId=" + radioStat.radioId); 4805 pw.println("totalRadioOnTimeMs=" + radioStat.totalRadioOnTimeMs); 4806 pw.println("totalRadioTxTimeMs=" + radioStat.totalRadioTxTimeMs); 4807 pw.println("totalRadioRxTimeMs=" + radioStat.totalRadioRxTimeMs); 4808 pw.println("totalScanTimeMs=" + radioStat.totalScanTimeMs); 4809 pw.println("totalNanScanTimeMs=" + radioStat.totalNanScanTimeMs); 4810 pw.println("totalBackgroundScanTimeMs=" + radioStat.totalBackgroundScanTimeMs); 4811 pw.println("totalRoamScanTimeMs=" + radioStat.totalRoamScanTimeMs); 4812 pw.println("totalPnoScanTimeMs=" + radioStat.totalPnoScanTimeMs); 4813 pw.println("totalHotspot2ScanTimeMs=" + radioStat.totalHotspot2ScanTimeMs); 4814 } 4815 4816 pw.println("mWifiLogProto.connectToNetworkNotificationCount=" 4817 + mConnectToNetworkNotificationCount.toString()); 4818 pw.println("mWifiLogProto.connectToNetworkNotificationActionCount=" 4819 + mConnectToNetworkNotificationActionCount.toString()); 4820 pw.println("mWifiLogProto.openNetworkRecommenderBlocklistSize=" 4821 + mOpenNetworkRecommenderBlocklistSize); 4822 pw.println("mWifiLogProto.isWifiNetworksAvailableNotificationOn=" 4823 + mIsWifiNetworksAvailableNotificationOn); 4824 pw.println("mWifiLogProto.numOpenNetworkRecommendationUpdates=" 4825 + mNumOpenNetworkRecommendationUpdates); 4826 pw.println("mWifiLogProto.numOpenNetworkConnectMessageFailedToSend=" 4827 + mNumOpenNetworkConnectMessageFailedToSend); 4828 4829 pw.println("mWifiLogProto.observedHotspotR1ApInScanHistogram=" 4830 + mObservedHotspotR1ApInScanHistogram); 4831 pw.println("mWifiLogProto.observedHotspotR2ApInScanHistogram=" 4832 + mObservedHotspotR2ApInScanHistogram); 4833 pw.println("mWifiLogProto.observedHotspotR3ApInScanHistogram=" 4834 + mObservedHotspotR3ApInScanHistogram); 4835 pw.println("mWifiLogProto.observedHotspotR1EssInScanHistogram=" 4836 + mObservedHotspotR1EssInScanHistogram); 4837 pw.println("mWifiLogProto.observedHotspotR2EssInScanHistogram=" 4838 + mObservedHotspotR2EssInScanHistogram); 4839 pw.println("mWifiLogProto.observedHotspotR3EssInScanHistogram=" 4840 + mObservedHotspotR3EssInScanHistogram); 4841 pw.println("mWifiLogProto.observedHotspotR1ApsPerEssInScanHistogram=" 4842 + mObservedHotspotR1ApsPerEssInScanHistogram); 4843 pw.println("mWifiLogProto.observedHotspotR2ApsPerEssInScanHistogram=" 4844 + mObservedHotspotR2ApsPerEssInScanHistogram); 4845 pw.println("mWifiLogProto.observedHotspotR3ApsPerEssInScanHistogram=" 4846 + mObservedHotspotR3ApsPerEssInScanHistogram); 4847 4848 pw.println("mWifiLogProto.observed80211mcSupportingApsInScanHistogram" 4849 + mObserved80211mcApInScanHistogram); 4850 pw.println("mWifiLogProto.bssidBlocklistStats:"); 4851 pw.println(mBssidBlocklistStats.toString()); 4852 4853 pw.println("mSoftApTetheredEvents:"); 4854 for (SoftApConnectedClientsEvent event : mSoftApEventListTethered) { 4855 StringBuilder eventLine = new StringBuilder(); 4856 eventLine.append("event_type=" + event.eventType); 4857 eventLine.append(",time_stamp_millis=" + event.timeStampMillis); 4858 eventLine.append(",num_connected_clients=" + event.numConnectedClients); 4859 eventLine.append(",num_connected_clients_on_current_frequency=" 4860 + event.numConnectedClientsOnCurrentFrequency); 4861 eventLine.append(",channel_frequency=" + event.channelFrequency); 4862 eventLine.append(",channel_bandwidth=" + event.channelBandwidth); 4863 eventLine.append(",generation=" + event.generation); 4864 eventLine.append(",max_num_clients_setting_in_softap_configuration=" 4865 + event.maxNumClientsSettingInSoftapConfiguration); 4866 eventLine.append(",max_num_clients_setting_in_softap_capability=" 4867 + event.maxNumClientsSettingInSoftapCapability); 4868 eventLine.append(",shutdown_timeout_setting_in_softap_configuration=" 4869 + event.shutdownTimeoutSettingInSoftapConfiguration); 4870 eventLine.append(",default_shutdown_timeout_setting=" 4871 + event.defaultShutdownTimeoutSetting); 4872 eventLine.append(",client_control_is_enabled=" + event.clientControlIsEnabled); 4873 pw.println(eventLine.toString()); 4874 } 4875 pw.println("mSoftApLocalOnlyEvents:"); 4876 for (SoftApConnectedClientsEvent event : mSoftApEventListLocalOnly) { 4877 StringBuilder eventLine = new StringBuilder(); 4878 eventLine.append("event_type=" + event.eventType); 4879 eventLine.append(",time_stamp_millis=" + event.timeStampMillis); 4880 eventLine.append(",num_connected_clients=" + event.numConnectedClients); 4881 eventLine.append(",num_connected_clients_on_current_frequency=" 4882 + event.numConnectedClientsOnCurrentFrequency); 4883 eventLine.append(",channel_frequency=" + event.channelFrequency); 4884 eventLine.append(",channel_bandwidth=" + event.channelBandwidth); 4885 eventLine.append(",generation=" + event.generation); 4886 eventLine.append(",max_num_clients_setting_in_softap_configuration=" 4887 + event.maxNumClientsSettingInSoftapConfiguration); 4888 eventLine.append(",max_num_clients_setting_in_softap_capability=" 4889 + event.maxNumClientsSettingInSoftapCapability); 4890 eventLine.append(",shutdown_timeout_setting_in_softap_configuration=" 4891 + event.shutdownTimeoutSettingInSoftapConfiguration); 4892 eventLine.append(",default_shutdown_timeout_setting=" 4893 + event.defaultShutdownTimeoutSetting); 4894 eventLine.append(",client_control_is_enabled=" + event.clientControlIsEnabled); 4895 pw.println(eventLine.toString()); 4896 } 4897 4898 mWifiPowerMetrics.dump(pw); 4899 mWifiWakeMetrics.dump(pw); 4900 4901 pw.println("mWifiLogProto.isMacRandomizationOn=" 4902 + mContext.getResources().getBoolean( 4903 R.bool.config_wifi_connected_mac_randomization_supported)); 4904 pw.println("mWifiLogProto.scoreExperimentId=" + mWifiLogProto.scoreExperimentId); 4905 pw.println("mExperimentValues.wifiDataStallMinTxBad=" 4906 + mContext.getResources().getInteger( 4907 R.integer.config_wifiDataStallMinTxBad)); 4908 pw.println("mExperimentValues.wifiDataStallMinTxSuccessWithoutRx=" 4909 + mContext.getResources().getInteger( 4910 R.integer.config_wifiDataStallMinTxSuccessWithoutRx)); 4911 pw.println("mExperimentValues.linkSpeedCountsLoggingEnabled=" 4912 + mContext.getResources().getBoolean( 4913 R.bool.config_wifiLinkSpeedMetricsEnabled)); 4914 pw.println("mExperimentValues.dataStallDurationMs=" 4915 + mExperimentValues.dataStallDurationMs); 4916 pw.println("mExperimentValues.dataStallTxTputThrKbps=" 4917 + mExperimentValues.dataStallTxTputThrKbps); 4918 pw.println("mExperimentValues.dataStallRxTputThrKbps=" 4919 + mExperimentValues.dataStallRxTputThrKbps); 4920 pw.println("mExperimentValues.dataStallTxPerThr=" 4921 + mExperimentValues.dataStallTxPerThr); 4922 pw.println("mExperimentValues.dataStallCcaLevelThr=" 4923 + mExperimentValues.dataStallCcaLevelThr); 4924 pw.println("WifiIsUnusableEventList: "); 4925 for (WifiIsUnusableWithTime event : mWifiIsUnusableList) { 4926 pw.println(event); 4927 } 4928 pw.println("Hardware Version: " + SystemProperties.get("ro.boot.revision", "")); 4929 4930 pw.println("mWifiUsabilityStatsEntriesList:"); 4931 for (WifiUsabilityStatsEntry stats : mWifiUsabilityStatsEntriesList) { 4932 printWifiUsabilityStatsEntry(pw, stats); 4933 } 4934 pw.println("mWifiUsabilityStatsList:"); 4935 for (WifiUsabilityStats stats : mWifiUsabilityStatsListGood) { 4936 pw.println("\nlabel=" + stats.label); 4937 pw.println("\ntrigger_type=" + stats.triggerType); 4938 pw.println("\ntime_stamp_ms=" + stats.timeStampMs); 4939 for (WifiUsabilityStatsEntry entry : stats.stats) { 4940 printWifiUsabilityStatsEntry(pw, entry); 4941 } 4942 } 4943 for (WifiUsabilityStats stats : mWifiUsabilityStatsListBad) { 4944 pw.println("\nlabel=" + stats.label); 4945 pw.println("\ntrigger_type=" + stats.triggerType); 4946 pw.println("\ntime_stamp_ms=" + stats.timeStampMs); 4947 for (WifiUsabilityStatsEntry entry : stats.stats) { 4948 printWifiUsabilityStatsEntry(pw, entry); 4949 } 4950 } 4951 4952 pw.println("mMobilityStatePnoStatsMap:"); 4953 for (int i = 0; i < mMobilityStatePnoStatsMap.size(); i++) { 4954 printDeviceMobilityStatePnoScanStats(pw, mMobilityStatePnoStatsMap.valueAt(i)); 4955 } 4956 4957 mWifiP2pMetrics.dump(pw); 4958 pw.println("mDppMetrics:"); 4959 mDppMetrics.dump(pw); 4960 4961 pw.println("mWifiConfigStoreReadDurationHistogram:" 4962 + mWifiConfigStoreReadDurationHistogram.toString()); 4963 pw.println("mWifiConfigStoreWriteDurationHistogram:" 4964 + mWifiConfigStoreWriteDurationHistogram.toString()); 4965 4966 pw.println("mLinkProbeSuccessRssiCounts:" + mLinkProbeSuccessRssiCounts); 4967 pw.println("mLinkProbeFailureRssiCounts:" + mLinkProbeFailureRssiCounts); 4968 pw.println("mLinkProbeSuccessLinkSpeedCounts:" + mLinkProbeSuccessLinkSpeedCounts); 4969 pw.println("mLinkProbeFailureLinkSpeedCounts:" + mLinkProbeFailureLinkSpeedCounts); 4970 pw.println("mLinkProbeSuccessSecondsSinceLastTxSuccessHistogram:" 4971 + mLinkProbeSuccessSecondsSinceLastTxSuccessHistogram); 4972 pw.println("mLinkProbeFailureSecondsSinceLastTxSuccessHistogram:" 4973 + mLinkProbeFailureSecondsSinceLastTxSuccessHistogram); 4974 pw.println("mLinkProbeSuccessElapsedTimeMsHistogram:" 4975 + mLinkProbeSuccessElapsedTimeMsHistogram); 4976 pw.println("mLinkProbeFailureReasonCounts:" + mLinkProbeFailureReasonCounts); 4977 pw.println("mLinkProbeExperimentProbeCounts:" + mLinkProbeExperimentProbeCounts); 4978 4979 pw.println("mNetworkSelectionExperimentPairNumChoicesCounts:" 4980 + mNetworkSelectionExperimentPairNumChoicesCounts); 4981 pw.println("mLinkProbeStaEventCount:" + mLinkProbeStaEventCount); 4982 4983 pw.println("mWifiNetworkRequestApiLog:\n" + mWifiNetworkRequestApiLog); 4984 pw.println("mWifiNetworkRequestApiMatchSizeHistogram:\n" 4985 + mWifiNetworkRequestApiMatchSizeHistogram); 4986 pw.println("mWifiNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram:\n" 4987 + mWifiNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram); 4988 pw.println("mWifiNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram:\n" 4989 + mWifiNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram); 4990 pw.println("mWifiNetworkRequestApiConcurrentConnectionDurationSecHistogram:\n" 4991 + mWifiNetworkRequestApiConcurrentConnectionDurationSecHistogram); 4992 pw.println("mWifiNetworkSuggestionApiLog:\n" + mWifiNetworkSuggestionApiLog); 4993 pw.println("mWifiNetworkSuggestionApiMatchSizeHistogram:\n" 4994 + mWifiNetworkSuggestionApiListSizeHistogram); 4995 pw.println("mWifiNetworkSuggestionApiAppTypeCounter:\n" 4996 + mWifiNetworkSuggestionApiAppTypeCounter); 4997 pw.println("mWifiNetworkSuggestionPriorityGroups:\n" 4998 + mWifiNetworkSuggestionPriorityGroups.toString()); 4999 pw.println("mWifiNetworkSuggestionCoexistSavedNetworks:\n" 5000 + mWifiNetworkSuggestionCoexistSavedNetworks.toString()); 5001 printUserApprovalSuggestionAppReaction(pw); 5002 printUserApprovalCarrierReaction(pw); 5003 pw.println("mNetworkIdToNominatorId:\n" + mNetworkIdToNominatorId); 5004 pw.println("mWifiLockStats:\n" + mWifiLockStats); 5005 pw.println("mWifiLockHighPerfAcqDurationSecHistogram:\n" 5006 + mWifiLockHighPerfAcqDurationSecHistogram); 5007 pw.println("mWifiLockLowLatencyAcqDurationSecHistogram:\n" 5008 + mWifiLockLowLatencyAcqDurationSecHistogram); 5009 pw.println("mWifiLockHighPerfActiveSessionDurationSecHistogram:\n" 5010 + mWifiLockHighPerfActiveSessionDurationSecHistogram); 5011 pw.println("mWifiLockLowLatencyActiveSessionDurationSecHistogram:\n" 5012 + mWifiLockLowLatencyActiveSessionDurationSecHistogram); 5013 pw.println("mWifiToggleStats:\n" + mWifiToggleStats); 5014 pw.println("mWifiLogProto.numAddOrUpdateNetworkCalls=" 5015 + mWifiLogProto.numAddOrUpdateNetworkCalls); 5016 pw.println("mWifiLogProto.numEnableNetworkCalls=" 5017 + mWifiLogProto.numEnableNetworkCalls); 5018 5019 pw.println("mWifiLogProto.txLinkSpeedCount2g=" + mTxLinkSpeedCount2g); 5020 pw.println("mWifiLogProto.txLinkSpeedCount5gLow=" + mTxLinkSpeedCount5gLow); 5021 pw.println("mWifiLogProto.txLinkSpeedCount5gMid=" + mTxLinkSpeedCount5gMid); 5022 pw.println("mWifiLogProto.txLinkSpeedCount5gHigh=" + mTxLinkSpeedCount5gHigh); 5023 pw.println("mWifiLogProto.txLinkSpeedCount6gLow=" + mTxLinkSpeedCount6gLow); 5024 pw.println("mWifiLogProto.txLinkSpeedCount6gMid=" + mTxLinkSpeedCount6gMid); 5025 pw.println("mWifiLogProto.txLinkSpeedCount6gHigh=" + mTxLinkSpeedCount6gHigh); 5026 5027 pw.println("mWifiLogProto.rxLinkSpeedCount2g=" + mRxLinkSpeedCount2g); 5028 pw.println("mWifiLogProto.rxLinkSpeedCount5gLow=" + mRxLinkSpeedCount5gLow); 5029 pw.println("mWifiLogProto.rxLinkSpeedCount5gMid=" + mRxLinkSpeedCount5gMid); 5030 pw.println("mWifiLogProto.rxLinkSpeedCount5gHigh=" + mRxLinkSpeedCount5gHigh); 5031 pw.println("mWifiLogProto.rxLinkSpeedCount6gLow=" + mRxLinkSpeedCount6gLow); 5032 pw.println("mWifiLogProto.rxLinkSpeedCount6gMid=" + mRxLinkSpeedCount6gMid); 5033 pw.println("mWifiLogProto.rxLinkSpeedCount6gHigh=" + mRxLinkSpeedCount6gHigh); 5034 5035 pw.println("mWifiLogProto.numIpRenewalFailure=" 5036 + mWifiLogProto.numIpRenewalFailure); 5037 pw.println("mWifiLogProto.connectionDurationStats=" 5038 + mConnectionDurationStats.toString()); 5039 pw.println("mWifiLogProto.isExternalWifiScorerOn=" 5040 + mWifiLogProto.isExternalWifiScorerOn); 5041 pw.println("mWifiLogProto.wifiOffMetrics=" 5042 + mWifiOffMetrics.toString()); 5043 pw.println("mWifiLogProto.softApConfigLimitationMetrics=" 5044 + mSoftApConfigLimitationMetrics.toString()); 5045 pw.println("mChannelUtilizationHistogram2G:\n" 5046 + mChannelUtilizationHistogram2G); 5047 pw.println("mChannelUtilizationHistogramAbove2G:\n" 5048 + mChannelUtilizationHistogramAbove2G); 5049 pw.println("mTxThroughputMbpsHistogram2G:\n" 5050 + mTxThroughputMbpsHistogram2G); 5051 pw.println("mRxThroughputMbpsHistogram2G:\n" 5052 + mRxThroughputMbpsHistogram2G); 5053 pw.println("mTxThroughputMbpsHistogramAbove2G:\n" 5054 + mTxThroughputMbpsHistogramAbove2G); 5055 pw.println("mRxThroughputMbpsHistogramAbove2G:\n" 5056 + mRxThroughputMbpsHistogramAbove2G); 5057 pw.println("mCarrierWifiMetrics:\n" 5058 + mCarrierWifiMetrics); 5059 pw.println(firstConnectAfterBootStatsToString(mFirstConnectAfterBootStats)); 5060 pw.println(wifiToWifiSwitchStatsToString(mWifiToWifiSwitchStats)); 5061 5062 dumpInitPartialScanMetrics(pw); 5063 } 5064 } 5065 } 5066 dumpInitPartialScanMetrics(PrintWriter pw)5067 private void dumpInitPartialScanMetrics(PrintWriter pw) { 5068 pw.println("mInitPartialScanTotalCount:\n" + mInitPartialScanTotalCount); 5069 pw.println("mInitPartialScanSuccessCount:\n" + mInitPartialScanSuccessCount); 5070 pw.println("mInitPartialScanFailureCount:\n" + mInitPartialScanFailureCount); 5071 pw.println("mInitPartialScanSuccessHistogram:\n" + mInitPartialScanSuccessHistogram); 5072 pw.println("mInitPartialScanFailureHistogram:\n" + mInitPartialScanFailureHistogram); 5073 } 5074 printWifiUsabilityStatsEntry(PrintWriter pw, WifiUsabilityStatsEntry entry)5075 private void printWifiUsabilityStatsEntry(PrintWriter pw, WifiUsabilityStatsEntry entry) { 5076 StringBuilder line = new StringBuilder(); 5077 line.append("timestamp_ms=" + entry.timeStampMs); 5078 line.append(",rssi=" + entry.rssi); 5079 line.append(",link_speed_mbps=" + entry.linkSpeedMbps); 5080 line.append(",total_tx_success=" + entry.totalTxSuccess); 5081 line.append(",total_tx_retries=" + entry.totalTxRetries); 5082 line.append(",total_tx_bad=" + entry.totalTxBad); 5083 line.append(",total_rx_success=" + entry.totalRxSuccess); 5084 if (entry.radioStats != null) { 5085 for (RadioStats radioStat : entry.radioStats) { 5086 line.append(",Radio Stats from radio_id=" + radioStat.radioId); 5087 line.append(",radio_on_time_ms=" + radioStat.totalRadioOnTimeMs); 5088 line.append(",radio_tx_time_ms=" + radioStat.totalRadioTxTimeMs); 5089 line.append(",radio_rx_time_ms=" + radioStat.totalRadioRxTimeMs); 5090 line.append(",scan_time_ms=" + radioStat.totalScanTimeMs); 5091 line.append(",nan_scan_time_ms=" + radioStat.totalNanScanTimeMs); 5092 line.append(",background_scan_time_ms=" + radioStat.totalBackgroundScanTimeMs); 5093 line.append(",roam_scan_time_ms=" + radioStat.totalRoamScanTimeMs); 5094 line.append(",pno_scan_time_ms=" + radioStat.totalPnoScanTimeMs); 5095 line.append(",hotspot_2_scan_time_ms=" + radioStat.totalHotspot2ScanTimeMs); 5096 } 5097 } 5098 line.append(",total_radio_on_time_ms=" + entry.totalRadioOnTimeMs); 5099 line.append(",total_radio_tx_time_ms=" + entry.totalRadioTxTimeMs); 5100 line.append(",total_radio_rx_time_ms=" + entry.totalRadioRxTimeMs); 5101 line.append(",total_scan_time_ms=" + entry.totalScanTimeMs); 5102 line.append(",total_nan_scan_time_ms=" + entry.totalNanScanTimeMs); 5103 line.append(",total_background_scan_time_ms=" + entry.totalBackgroundScanTimeMs); 5104 line.append(",total_roam_scan_time_ms=" + entry.totalRoamScanTimeMs); 5105 line.append(",total_pno_scan_time_ms=" + entry.totalPnoScanTimeMs); 5106 line.append(",total_hotspot_2_scan_time_ms=" + entry.totalHotspot2ScanTimeMs); 5107 line.append(",wifi_score=" + entry.wifiScore); 5108 line.append(",wifi_usability_score=" + entry.wifiUsabilityScore); 5109 line.append(",seq_num_to_framework=" + entry.seqNumToFramework); 5110 line.append(",prediction_horizon_sec=" + entry.predictionHorizonSec); 5111 line.append(",total_cca_busy_freq_time_ms=" + entry.totalCcaBusyFreqTimeMs); 5112 line.append(",total_radio_on_freq_time_ms=" + entry.totalRadioOnFreqTimeMs); 5113 line.append(",total_beacon_rx=" + entry.totalBeaconRx); 5114 line.append(",probe_status_since_last_update=" + entry.probeStatusSinceLastUpdate); 5115 line.append(",probe_elapsed_time_ms_since_last_update=" 5116 + entry.probeElapsedTimeSinceLastUpdateMs); 5117 line.append(",probe_mcs_rate_since_last_update=" + entry.probeMcsRateSinceLastUpdate); 5118 line.append(",rx_link_speed_mbps=" + entry.rxLinkSpeedMbps); 5119 line.append(",seq_num_inside_framework=" + entry.seqNumInsideFramework); 5120 line.append(",is_same_bssid_and_freq=" + entry.isSameBssidAndFreq); 5121 line.append(",device_mobility_state=" + entry.deviceMobilityState); 5122 line.append(",time_slice_duty_cycle_in_percent=" + entry.timeSliceDutyCycleInPercent); 5123 if (entry.contentionTimeStats != null) { 5124 for (ContentionTimeStats stat : entry.contentionTimeStats) { 5125 line.append(",access_category=" + stat.accessCategory); 5126 line.append(",contention_time_min_micros=" + stat.contentionTimeMinMicros); 5127 line.append(",contention_time_max_micros=" + stat.contentionTimeMaxMicros); 5128 line.append(",contention_time_avg_micros=" + stat.contentionTimeAvgMicros); 5129 line.append(",contention_num_samples=" + stat.contentionNumSamples); 5130 } 5131 } 5132 line.append(",channel_utilization_ratio=" + entry.channelUtilizationRatio); 5133 line.append(",is_throughput_sufficient=" + entry.isThroughputSufficient); 5134 line.append(",is_wifi_scoring_enabled=" + entry.isWifiScoringEnabled); 5135 line.append(",is_cellular_data_available=" + entry.isCellularDataAvailable); 5136 line.append(",sta_count=" + entry.staCount); 5137 line.append(",channel_utilization=" + entry.channelUtilization); 5138 if (entry.rateStats != null) { 5139 for (RateStats rateStat : entry.rateStats) { 5140 line.append(",preamble=" + rateStat.preamble); 5141 line.append(",nss=" + rateStat.nss); 5142 line.append(",bw=" + rateStat.bw); 5143 line.append(",rate_mcs_idx=" + rateStat.rateMcsIdx); 5144 line.append(",bit_rate_in_kbps=" + rateStat.bitRateInKbps); 5145 line.append(",tx_mpdu=" + rateStat.txMpdu); 5146 line.append(",rx_mpdu=" + rateStat.rxMpdu); 5147 line.append(",mpdu_lost=" + rateStat.mpduLost); 5148 line.append(",retries=" + rateStat.retries); 5149 } 5150 } 5151 pw.println(line.toString()); 5152 } 5153 printDeviceMobilityStatePnoScanStats(PrintWriter pw, DeviceMobilityStatePnoScanStats stats)5154 private void printDeviceMobilityStatePnoScanStats(PrintWriter pw, 5155 DeviceMobilityStatePnoScanStats stats) { 5156 StringBuilder line = new StringBuilder(); 5157 line.append("device_mobility_state=" + stats.deviceMobilityState); 5158 line.append(",num_times_entered_state=" + stats.numTimesEnteredState); 5159 line.append(",total_duration_ms=" + stats.totalDurationMs); 5160 line.append(",pno_duration_ms=" + stats.pnoDurationMs); 5161 pw.println(line.toString()); 5162 } 5163 printUserApprovalSuggestionAppReaction(PrintWriter pw)5164 private void printUserApprovalSuggestionAppReaction(PrintWriter pw) { 5165 pw.println("mUserApprovalSuggestionAppUiUserReaction:"); 5166 for (UserReaction event : mUserApprovalSuggestionAppUiReactionList) { 5167 pw.println(event); 5168 } 5169 } 5170 printUserApprovalCarrierReaction(PrintWriter pw)5171 private void printUserApprovalCarrierReaction(PrintWriter pw) { 5172 pw.println("mUserApprovalCarrierUiUserReaction:"); 5173 for (UserReaction event : mUserApprovalCarrierUiReactionList) { 5174 pw.println(event); 5175 } 5176 } 5177 5178 /** 5179 * Update various counts of saved network types 5180 * @param networks List of WifiConfigurations representing all saved networks, must not be null 5181 */ updateSavedNetworks(List<WifiConfiguration> networks)5182 public void updateSavedNetworks(List<WifiConfiguration> networks) { 5183 synchronized (mLock) { 5184 mWifiLogProto.numSavedNetworks = networks.size(); 5185 mWifiLogProto.numSavedNetworksWithMacRandomization = 0; 5186 mWifiLogProto.numOpenNetworks = 0; 5187 mWifiLogProto.numLegacyPersonalNetworks = 0; 5188 mWifiLogProto.numLegacyEnterpriseNetworks = 0; 5189 mWifiLogProto.numEnhancedOpenNetworks = 0; 5190 mWifiLogProto.numWpa3PersonalNetworks = 0; 5191 mWifiLogProto.numWpa3EnterpriseNetworks = 0; 5192 mWifiLogProto.numWapiPersonalNetworks = 0; 5193 mWifiLogProto.numWapiEnterpriseNetworks = 0; 5194 mWifiLogProto.numNetworksAddedByUser = 0; 5195 mWifiLogProto.numNetworksAddedByApps = 0; 5196 mWifiLogProto.numHiddenNetworks = 0; 5197 mWifiLogProto.numPasspointNetworks = 0; 5198 5199 for (WifiConfiguration config : networks) { 5200 if (config.isSecurityType(WifiConfiguration.SECURITY_TYPE_OPEN)) { 5201 mWifiLogProto.numOpenNetworks++; 5202 } else if (config.isSecurityType(WifiConfiguration.SECURITY_TYPE_OWE)) { 5203 mWifiLogProto.numEnhancedOpenNetworks++; 5204 } else if (config.isSecurityType(WifiConfiguration.SECURITY_TYPE_WAPI_PSK)) { 5205 mWifiLogProto.numWapiPersonalNetworks++; 5206 } else if (config.isEnterprise()) { 5207 if (config.isSecurityType( 5208 WifiConfiguration.SECURITY_TYPE_EAP_WPA3_ENTERPRISE_192_BIT)) { 5209 mWifiLogProto.numWpa3EnterpriseNetworks++; 5210 } else if (config.isSecurityType( 5211 WifiConfiguration.SECURITY_TYPE_WAPI_CERT)) { 5212 mWifiLogProto.numWapiEnterpriseNetworks++; 5213 } else { 5214 mWifiLogProto.numLegacyEnterpriseNetworks++; 5215 } 5216 } else { 5217 if (config.isSecurityType(WifiConfiguration.SECURITY_TYPE_PSK)) { 5218 mWifiLogProto.numLegacyPersonalNetworks++; 5219 } 5220 else if (config.isSecurityType(WifiConfiguration.SECURITY_TYPE_SAE)) { 5221 mWifiLogProto.numWpa3PersonalNetworks++; 5222 } 5223 } 5224 mWifiLogProto.numNetworksAddedByApps++; 5225 if (config.hiddenSSID) { 5226 mWifiLogProto.numHiddenNetworks++; 5227 } 5228 if (config.isPasspoint()) { 5229 mWifiLogProto.numPasspointNetworks++; 5230 } 5231 if (config.macRandomizationSetting != WifiConfiguration.RANDOMIZATION_NONE) { 5232 mWifiLogProto.numSavedNetworksWithMacRandomization++; 5233 } 5234 } 5235 } 5236 } 5237 5238 /** 5239 * Update metrics for saved Passpoint profiles. 5240 * 5241 * @param numSavedProfiles The number of saved Passpoint profiles 5242 * @param numConnectedProfiles The number of saved Passpoint profiles that have ever resulted 5243 * in a successful network connection 5244 */ updateSavedPasspointProfiles(int numSavedProfiles, int numConnectedProfiles)5245 public void updateSavedPasspointProfiles(int numSavedProfiles, int numConnectedProfiles) { 5246 synchronized (mLock) { 5247 mWifiLogProto.numPasspointProviders = numSavedProfiles; 5248 mWifiLogProto.numPasspointProvidersSuccessfullyConnected = numConnectedProfiles; 5249 } 5250 } 5251 5252 /** 5253 * Update number of times for type of saved Passpoint profile. 5254 * 5255 * @param providers Passpoint providers installed on the device. 5256 */ updateSavedPasspointProfilesInfo( Map<String, PasspointProvider> providers)5257 public void updateSavedPasspointProfilesInfo( 5258 Map<String, PasspointProvider> providers) { 5259 int passpointType; 5260 int eapType; 5261 PasspointConfiguration config; 5262 synchronized (mLock) { 5263 mInstalledPasspointProfileTypeForR1.clear(); 5264 mInstalledPasspointProfileTypeForR2.clear(); 5265 for (Map.Entry<String, PasspointProvider> entry : providers.entrySet()) { 5266 config = entry.getValue().getConfig(); 5267 if (config.getCredential().getUserCredential() != null) { 5268 eapType = EAPConstants.EAP_TTLS; 5269 } else if (config.getCredential().getCertCredential() != null) { 5270 eapType = EAPConstants.EAP_TLS; 5271 } else if (config.getCredential().getSimCredential() != null) { 5272 eapType = config.getCredential().getSimCredential().getEapType(); 5273 } else { 5274 eapType = -1; 5275 } 5276 switch (eapType) { 5277 case EAPConstants.EAP_TLS: 5278 passpointType = WifiMetricsProto.PasspointProfileTypeCount.TYPE_EAP_TLS; 5279 break; 5280 case EAPConstants.EAP_TTLS: 5281 passpointType = WifiMetricsProto.PasspointProfileTypeCount.TYPE_EAP_TTLS; 5282 break; 5283 case EAPConstants.EAP_SIM: 5284 passpointType = WifiMetricsProto.PasspointProfileTypeCount.TYPE_EAP_SIM; 5285 break; 5286 case EAPConstants.EAP_AKA: 5287 passpointType = WifiMetricsProto.PasspointProfileTypeCount.TYPE_EAP_AKA; 5288 break; 5289 case EAPConstants.EAP_AKA_PRIME: 5290 passpointType = 5291 WifiMetricsProto.PasspointProfileTypeCount.TYPE_EAP_AKA_PRIME; 5292 break; 5293 default: 5294 passpointType = WifiMetricsProto.PasspointProfileTypeCount.TYPE_UNKNOWN; 5295 5296 } 5297 if (config.validateForR2()) { 5298 mInstalledPasspointProfileTypeForR2.increment(passpointType); 5299 } else { 5300 mInstalledPasspointProfileTypeForR1.increment(passpointType); 5301 } 5302 } 5303 } 5304 } 5305 5306 /** 5307 * Increment initial partial scan count 5308 */ incrementInitialPartialScanCount()5309 public void incrementInitialPartialScanCount() { 5310 synchronized (mLock) { 5311 mInitPartialScanTotalCount++; 5312 } 5313 } 5314 5315 /** 5316 * Report of initial partial scan 5317 * @param channelCount number of channels used in this scan 5318 * @param status true if scan resulted in a network connection attempt, false otherwise 5319 */ reportInitialPartialScan(int channelCount, boolean status)5320 public void reportInitialPartialScan(int channelCount, boolean status) { 5321 synchronized (mLock) { 5322 if (status) { 5323 mInitPartialScanSuccessCount++; 5324 mInitPartialScanSuccessHistogram.increment(channelCount); 5325 } else { 5326 mInitPartialScanFailureCount++; 5327 mInitPartialScanFailureHistogram.increment(channelCount); 5328 } 5329 } 5330 } 5331 5332 /** 5333 * Put all metrics that were being tracked separately into mWifiLogProto 5334 */ consolidateProto()5335 private void consolidateProto() { 5336 List<WifiMetricsProto.RssiPollCount> rssis = new ArrayList<>(); 5337 synchronized (mLock) { 5338 mWifiLogProto.connectionEvent = mConnectionEventList 5339 .stream() 5340 // Exclude active un-ended connection events 5341 .filter(connectionEvent -> 5342 !mCurrentConnectionEventPerIface.containsValue(connectionEvent)) 5343 // unwrap WifiMetrics.ConnectionEvent to get WifiMetricsProto.ConnectionEvent 5344 .map(connectionEvent -> connectionEvent.mConnectionEvent) 5345 .toArray(WifiMetricsProto.ConnectionEvent[]::new); 5346 5347 //Convert the SparseIntArray of scanReturnEntry integers into ScanReturnEntry proto list 5348 mWifiLogProto.scanReturnEntries = 5349 new WifiMetricsProto.WifiLog.ScanReturnEntry[mScanReturnEntries.size()]; 5350 for (int i = 0; i < mScanReturnEntries.size(); i++) { 5351 mWifiLogProto.scanReturnEntries[i] = new WifiMetricsProto.WifiLog.ScanReturnEntry(); 5352 mWifiLogProto.scanReturnEntries[i].scanReturnCode = mScanReturnEntries.keyAt(i); 5353 mWifiLogProto.scanReturnEntries[i].scanResultsCount = mScanReturnEntries.valueAt(i); 5354 } 5355 5356 // Convert the SparseIntArray of systemStateEntry into WifiSystemStateEntry proto list 5357 // This one is slightly more complex, as the Sparse are indexed with: 5358 // key: wifiState * 2 + isScreenOn, value: wifiStateCount 5359 mWifiLogProto.wifiSystemStateEntries = 5360 new WifiMetricsProto.WifiLog 5361 .WifiSystemStateEntry[mWifiSystemStateEntries.size()]; 5362 for (int i = 0; i < mWifiSystemStateEntries.size(); i++) { 5363 mWifiLogProto.wifiSystemStateEntries[i] = 5364 new WifiMetricsProto.WifiLog.WifiSystemStateEntry(); 5365 mWifiLogProto.wifiSystemStateEntries[i].wifiState = 5366 mWifiSystemStateEntries.keyAt(i) / 2; 5367 mWifiLogProto.wifiSystemStateEntries[i].wifiStateCount = 5368 mWifiSystemStateEntries.valueAt(i); 5369 mWifiLogProto.wifiSystemStateEntries[i].isScreenOn = 5370 (mWifiSystemStateEntries.keyAt(i) % 2) > 0; 5371 } 5372 mWifiLogProto.recordDurationSec = (int) ((mClock.getElapsedSinceBootMillis() / 1000) 5373 - mRecordStartTimeSec); 5374 5375 /** 5376 * Convert the SparseIntArrays of RSSI poll rssi, counts, and frequency to the 5377 * proto's repeated IntKeyVal array. 5378 */ 5379 for (Map.Entry<Integer, SparseIntArray> entry : mRssiPollCountsMap.entrySet()) { 5380 int frequency = entry.getKey(); 5381 SparseIntArray histogram = entry.getValue(); 5382 for (int i = 0; i < histogram.size(); i++) { 5383 WifiMetricsProto.RssiPollCount keyVal = new WifiMetricsProto.RssiPollCount(); 5384 keyVal.rssi = histogram.keyAt(i); 5385 keyVal.count = histogram.valueAt(i); 5386 keyVal.frequency = frequency; 5387 rssis.add(keyVal); 5388 } 5389 } 5390 mWifiLogProto.rssiPollRssiCount = rssis.toArray(mWifiLogProto.rssiPollRssiCount); 5391 5392 /** 5393 * Convert the SparseIntArray of RSSI delta rssi's and counts to the proto's repeated 5394 * IntKeyVal array. 5395 */ 5396 mWifiLogProto.rssiPollDeltaCount = 5397 new WifiMetricsProto.RssiPollCount[mRssiDeltaCounts.size()]; 5398 for (int i = 0; i < mRssiDeltaCounts.size(); i++) { 5399 mWifiLogProto.rssiPollDeltaCount[i] = new WifiMetricsProto.RssiPollCount(); 5400 mWifiLogProto.rssiPollDeltaCount[i].rssi = mRssiDeltaCounts.keyAt(i); 5401 mWifiLogProto.rssiPollDeltaCount[i].count = mRssiDeltaCounts.valueAt(i); 5402 } 5403 5404 /** 5405 * Add LinkSpeedCount objects from mLinkSpeedCounts to proto. 5406 */ 5407 mWifiLogProto.linkSpeedCounts = 5408 new WifiMetricsProto.LinkSpeedCount[mLinkSpeedCounts.size()]; 5409 for (int i = 0; i < mLinkSpeedCounts.size(); i++) { 5410 mWifiLogProto.linkSpeedCounts[i] = mLinkSpeedCounts.valueAt(i); 5411 } 5412 5413 /** 5414 * Convert the SparseIntArray of alert reasons and counts to the proto's repeated 5415 * IntKeyVal array. 5416 */ 5417 mWifiLogProto.alertReasonCount = 5418 new WifiMetricsProto.AlertReasonCount[mWifiAlertReasonCounts.size()]; 5419 for (int i = 0; i < mWifiAlertReasonCounts.size(); i++) { 5420 mWifiLogProto.alertReasonCount[i] = new WifiMetricsProto.AlertReasonCount(); 5421 mWifiLogProto.alertReasonCount[i].reason = mWifiAlertReasonCounts.keyAt(i); 5422 mWifiLogProto.alertReasonCount[i].count = mWifiAlertReasonCounts.valueAt(i); 5423 } 5424 5425 /** 5426 * Convert the SparseIntArray of Wifi Score and counts to proto's repeated 5427 * IntKeyVal array. 5428 */ 5429 mWifiLogProto.wifiScoreCount = 5430 new WifiMetricsProto.WifiScoreCount[mWifiScoreCounts.size()]; 5431 for (int score = 0; score < mWifiScoreCounts.size(); score++) { 5432 mWifiLogProto.wifiScoreCount[score] = new WifiMetricsProto.WifiScoreCount(); 5433 mWifiLogProto.wifiScoreCount[score].score = mWifiScoreCounts.keyAt(score); 5434 mWifiLogProto.wifiScoreCount[score].count = mWifiScoreCounts.valueAt(score); 5435 } 5436 5437 /** 5438 * Convert the SparseIntArray of Wifi Usability Score and counts to proto's repeated 5439 * IntKeyVal array. 5440 */ 5441 mWifiLogProto.wifiUsabilityScoreCount = 5442 new WifiMetricsProto.WifiUsabilityScoreCount[mWifiUsabilityScoreCounts.size()]; 5443 for (int scoreIdx = 0; scoreIdx < mWifiUsabilityScoreCounts.size(); scoreIdx++) { 5444 mWifiLogProto.wifiUsabilityScoreCount[scoreIdx] = 5445 new WifiMetricsProto.WifiUsabilityScoreCount(); 5446 mWifiLogProto.wifiUsabilityScoreCount[scoreIdx].score = 5447 mWifiUsabilityScoreCounts.keyAt(scoreIdx); 5448 mWifiLogProto.wifiUsabilityScoreCount[scoreIdx].count = 5449 mWifiUsabilityScoreCounts.valueAt(scoreIdx); 5450 } 5451 5452 /** 5453 * Convert the SparseIntArray of SoftAp Return codes and counts to proto's repeated 5454 * IntKeyVal array. 5455 */ 5456 int codeCounts = mSoftApManagerReturnCodeCounts.size(); 5457 mWifiLogProto.softApReturnCode = new WifiMetricsProto.SoftApReturnCodeCount[codeCounts]; 5458 for (int sapCode = 0; sapCode < codeCounts; sapCode++) { 5459 mWifiLogProto.softApReturnCode[sapCode] = 5460 new WifiMetricsProto.SoftApReturnCodeCount(); 5461 mWifiLogProto.softApReturnCode[sapCode].startResult = 5462 mSoftApManagerReturnCodeCounts.keyAt(sapCode); 5463 mWifiLogProto.softApReturnCode[sapCode].count = 5464 mSoftApManagerReturnCodeCounts.valueAt(sapCode); 5465 } 5466 5467 /** 5468 * Convert StaEventList to array of StaEvents 5469 */ 5470 mWifiLogProto.staEventList = new StaEvent[mStaEventList.size()]; 5471 for (int i = 0; i < mStaEventList.size(); i++) { 5472 mWifiLogProto.staEventList[i] = mStaEventList.get(i).staEvent; 5473 } 5474 mWifiLogProto.userActionEvents = new UserActionEvent[mUserActionEventList.size()]; 5475 for (int i = 0; i < mUserActionEventList.size(); i++) { 5476 mWifiLogProto.userActionEvents[i] = mUserActionEventList.get(i).toProto(); 5477 } 5478 mWifiLogProto.totalSsidsInScanHistogram = 5479 makeNumConnectableNetworksBucketArray(mTotalSsidsInScanHistogram); 5480 mWifiLogProto.totalBssidsInScanHistogram = 5481 makeNumConnectableNetworksBucketArray(mTotalBssidsInScanHistogram); 5482 mWifiLogProto.availableOpenSsidsInScanHistogram = 5483 makeNumConnectableNetworksBucketArray(mAvailableOpenSsidsInScanHistogram); 5484 mWifiLogProto.availableOpenBssidsInScanHistogram = 5485 makeNumConnectableNetworksBucketArray(mAvailableOpenBssidsInScanHistogram); 5486 mWifiLogProto.availableSavedSsidsInScanHistogram = 5487 makeNumConnectableNetworksBucketArray(mAvailableSavedSsidsInScanHistogram); 5488 mWifiLogProto.availableSavedBssidsInScanHistogram = 5489 makeNumConnectableNetworksBucketArray(mAvailableSavedBssidsInScanHistogram); 5490 mWifiLogProto.availableOpenOrSavedSsidsInScanHistogram = 5491 makeNumConnectableNetworksBucketArray( 5492 mAvailableOpenOrSavedSsidsInScanHistogram); 5493 mWifiLogProto.availableOpenOrSavedBssidsInScanHistogram = 5494 makeNumConnectableNetworksBucketArray( 5495 mAvailableOpenOrSavedBssidsInScanHistogram); 5496 mWifiLogProto.availableSavedPasspointProviderProfilesInScanHistogram = 5497 makeNumConnectableNetworksBucketArray( 5498 mAvailableSavedPasspointProviderProfilesInScanHistogram); 5499 mWifiLogProto.availableSavedPasspointProviderBssidsInScanHistogram = 5500 makeNumConnectableNetworksBucketArray( 5501 mAvailableSavedPasspointProviderBssidsInScanHistogram); 5502 mWifiLogProto.wifiAwareLog = mWifiAwareMetrics.consolidateProto(); 5503 mWifiLogProto.wifiRttLog = mRttMetrics.consolidateProto(); 5504 5505 mWifiLogProto.pnoScanMetrics = mPnoScanMetrics; 5506 mWifiLogProto.wifiLinkLayerUsageStats = mWifiLinkLayerUsageStats; 5507 mWifiLogProto.wifiLinkLayerUsageStats.radioStats = 5508 new WifiMetricsProto.RadioStats[mRadioStats.size()]; 5509 for (int i = 0; i < mRadioStats.size(); i++) { 5510 mWifiLogProto.wifiLinkLayerUsageStats.radioStats[i] = mRadioStats.valueAt(i); 5511 } 5512 5513 /** 5514 * Convert the SparseIntArray of "Connect to Network" notification types and counts to 5515 * proto's repeated IntKeyVal array. 5516 */ 5517 ConnectToNetworkNotificationAndActionCount[] notificationCountArray = 5518 new ConnectToNetworkNotificationAndActionCount[ 5519 mConnectToNetworkNotificationCount.size()]; 5520 for (int i = 0; i < mConnectToNetworkNotificationCount.size(); i++) { 5521 ConnectToNetworkNotificationAndActionCount keyVal = 5522 new ConnectToNetworkNotificationAndActionCount(); 5523 keyVal.notification = mConnectToNetworkNotificationCount.keyAt(i); 5524 keyVal.recommender = 5525 ConnectToNetworkNotificationAndActionCount.RECOMMENDER_OPEN; 5526 keyVal.count = mConnectToNetworkNotificationCount.valueAt(i); 5527 notificationCountArray[i] = keyVal; 5528 } 5529 mWifiLogProto.connectToNetworkNotificationCount = notificationCountArray; 5530 5531 /** 5532 * Convert the SparseIntArray of "Connect to Network" notification types and counts to 5533 * proto's repeated IntKeyVal array. 5534 */ 5535 ConnectToNetworkNotificationAndActionCount[] notificationActionCountArray = 5536 new ConnectToNetworkNotificationAndActionCount[ 5537 mConnectToNetworkNotificationActionCount.size()]; 5538 for (int i = 0; i < mConnectToNetworkNotificationActionCount.size(); i++) { 5539 ConnectToNetworkNotificationAndActionCount keyVal = 5540 new ConnectToNetworkNotificationAndActionCount(); 5541 int k = mConnectToNetworkNotificationActionCount.keyAt(i); 5542 keyVal.notification = k / CONNECT_TO_NETWORK_NOTIFICATION_ACTION_KEY_MULTIPLIER; 5543 keyVal.action = k % CONNECT_TO_NETWORK_NOTIFICATION_ACTION_KEY_MULTIPLIER; 5544 keyVal.recommender = 5545 ConnectToNetworkNotificationAndActionCount.RECOMMENDER_OPEN; 5546 keyVal.count = mConnectToNetworkNotificationActionCount.valueAt(i); 5547 notificationActionCountArray[i] = keyVal; 5548 } 5549 5550 mWifiLogProto.installedPasspointProfileTypeForR1 = 5551 convertPasspointProfilesToProto(mInstalledPasspointProfileTypeForR1); 5552 mWifiLogProto.installedPasspointProfileTypeForR2 = 5553 convertPasspointProfilesToProto(mInstalledPasspointProfileTypeForR2); 5554 5555 mWifiLogProto.connectToNetworkNotificationActionCount = notificationActionCountArray; 5556 5557 mWifiLogProto.openNetworkRecommenderBlocklistSize = 5558 mOpenNetworkRecommenderBlocklistSize; 5559 mWifiLogProto.isWifiNetworksAvailableNotificationOn = 5560 mIsWifiNetworksAvailableNotificationOn; 5561 mWifiLogProto.numOpenNetworkRecommendationUpdates = 5562 mNumOpenNetworkRecommendationUpdates; 5563 mWifiLogProto.numOpenNetworkConnectMessageFailedToSend = 5564 mNumOpenNetworkConnectMessageFailedToSend; 5565 5566 mWifiLogProto.observedHotspotR1ApsInScanHistogram = 5567 makeNumConnectableNetworksBucketArray(mObservedHotspotR1ApInScanHistogram); 5568 mWifiLogProto.observedHotspotR2ApsInScanHistogram = 5569 makeNumConnectableNetworksBucketArray(mObservedHotspotR2ApInScanHistogram); 5570 mWifiLogProto.observedHotspotR3ApsInScanHistogram = 5571 makeNumConnectableNetworksBucketArray(mObservedHotspotR3ApInScanHistogram); 5572 mWifiLogProto.observedHotspotR1EssInScanHistogram = 5573 makeNumConnectableNetworksBucketArray(mObservedHotspotR1EssInScanHistogram); 5574 mWifiLogProto.observedHotspotR2EssInScanHistogram = 5575 makeNumConnectableNetworksBucketArray(mObservedHotspotR2EssInScanHistogram); 5576 mWifiLogProto.observedHotspotR3EssInScanHistogram = 5577 makeNumConnectableNetworksBucketArray(mObservedHotspotR3EssInScanHistogram); 5578 mWifiLogProto.observedHotspotR1ApsPerEssInScanHistogram = 5579 makeNumConnectableNetworksBucketArray( 5580 mObservedHotspotR1ApsPerEssInScanHistogram); 5581 mWifiLogProto.observedHotspotR2ApsPerEssInScanHistogram = 5582 makeNumConnectableNetworksBucketArray( 5583 mObservedHotspotR2ApsPerEssInScanHistogram); 5584 mWifiLogProto.observedHotspotR3ApsPerEssInScanHistogram = 5585 makeNumConnectableNetworksBucketArray( 5586 mObservedHotspotR3ApsPerEssInScanHistogram); 5587 5588 mWifiLogProto.observed80211McSupportingApsInScanHistogram = 5589 makeNumConnectableNetworksBucketArray(mObserved80211mcApInScanHistogram); 5590 5591 if (mSoftApEventListTethered.size() > 0) { 5592 mWifiLogProto.softApConnectedClientsEventsTethered = 5593 mSoftApEventListTethered.toArray( 5594 mWifiLogProto.softApConnectedClientsEventsTethered); 5595 } 5596 if (mSoftApEventListLocalOnly.size() > 0) { 5597 mWifiLogProto.softApConnectedClientsEventsLocalOnly = 5598 mSoftApEventListLocalOnly.toArray( 5599 mWifiLogProto.softApConnectedClientsEventsLocalOnly); 5600 } 5601 5602 mWifiLogProto.wifiPowerStats = mWifiPowerMetrics.buildProto(); 5603 mWifiLogProto.wifiRadioUsage = mWifiPowerMetrics.buildWifiRadioUsageProto(); 5604 mWifiLogProto.wifiWakeStats = mWifiWakeMetrics.buildProto(); 5605 mWifiLogProto.isMacRandomizationOn = mContext.getResources().getBoolean( 5606 R.bool.config_wifi_connected_mac_randomization_supported); 5607 mExperimentValues.linkSpeedCountsLoggingEnabled = mContext.getResources().getBoolean( 5608 R.bool.config_wifiLinkSpeedMetricsEnabled); 5609 mExperimentValues.wifiDataStallMinTxBad = mContext.getResources().getInteger( 5610 R.integer.config_wifiDataStallMinTxBad); 5611 mExperimentValues.wifiDataStallMinTxSuccessWithoutRx = 5612 mContext.getResources().getInteger( 5613 R.integer.config_wifiDataStallMinTxSuccessWithoutRx); 5614 mWifiLogProto.experimentValues = mExperimentValues; 5615 mWifiLogProto.wifiIsUnusableEventList = 5616 new WifiIsUnusableEvent[mWifiIsUnusableList.size()]; 5617 for (int i = 0; i < mWifiIsUnusableList.size(); i++) { 5618 mWifiLogProto.wifiIsUnusableEventList[i] = mWifiIsUnusableList.get(i).event; 5619 } 5620 mWifiLogProto.hardwareRevision = SystemProperties.get("ro.boot.revision", ""); 5621 5622 // Postprocessing on WifiUsabilityStats to upload an equal number of LABEL_GOOD and 5623 // LABEL_BAD WifiUsabilityStats 5624 final int numUsabilityStats = Math.min( 5625 Math.min(mWifiUsabilityStatsListBad.size(), 5626 mWifiUsabilityStatsListGood.size()), 5627 MAX_WIFI_USABILITY_STATS_PER_TYPE_TO_UPLOAD); 5628 LinkedList<WifiUsabilityStats> usabilityStatsGoodCopy = 5629 new LinkedList<>(mWifiUsabilityStatsListGood); 5630 LinkedList<WifiUsabilityStats> usabilityStatsBadCopy = 5631 new LinkedList<>(mWifiUsabilityStatsListBad); 5632 mWifiLogProto.wifiUsabilityStatsList = new WifiUsabilityStats[numUsabilityStats * 2]; 5633 for (int i = 0; i < numUsabilityStats; i++) { 5634 mWifiLogProto.wifiUsabilityStatsList[2 * i] = usabilityStatsGoodCopy.remove( 5635 mRand.nextInt(usabilityStatsGoodCopy.size())); 5636 mWifiLogProto.wifiUsabilityStatsList[2 * i + 1] = usabilityStatsBadCopy.remove( 5637 mRand.nextInt(usabilityStatsBadCopy.size())); 5638 } 5639 mWifiLogProto.mobilityStatePnoStatsList = 5640 new DeviceMobilityStatePnoScanStats[mMobilityStatePnoStatsMap.size()]; 5641 for (int i = 0; i < mMobilityStatePnoStatsMap.size(); i++) { 5642 mWifiLogProto.mobilityStatePnoStatsList[i] = mMobilityStatePnoStatsMap.valueAt(i); 5643 } 5644 mWifiLogProto.wifiP2PStats = mWifiP2pMetrics.consolidateProto(); 5645 mWifiLogProto.wifiDppLog = mDppMetrics.consolidateProto(); 5646 mWifiLogProto.wifiConfigStoreIo = new WifiMetricsProto.WifiConfigStoreIO(); 5647 mWifiLogProto.wifiConfigStoreIo.readDurations = 5648 makeWifiConfigStoreIODurationBucketArray(mWifiConfigStoreReadDurationHistogram); 5649 mWifiLogProto.wifiConfigStoreIo.writeDurations = 5650 makeWifiConfigStoreIODurationBucketArray( 5651 mWifiConfigStoreWriteDurationHistogram); 5652 5653 LinkProbeStats linkProbeStats = new LinkProbeStats(); 5654 linkProbeStats.successRssiCounts = mLinkProbeSuccessRssiCounts.toProto(); 5655 linkProbeStats.failureRssiCounts = mLinkProbeFailureRssiCounts.toProto(); 5656 linkProbeStats.successLinkSpeedCounts = mLinkProbeSuccessLinkSpeedCounts.toProto(); 5657 linkProbeStats.failureLinkSpeedCounts = mLinkProbeFailureLinkSpeedCounts.toProto(); 5658 linkProbeStats.successSecondsSinceLastTxSuccessHistogram = 5659 mLinkProbeSuccessSecondsSinceLastTxSuccessHistogram.toProto(); 5660 linkProbeStats.failureSecondsSinceLastTxSuccessHistogram = 5661 mLinkProbeFailureSecondsSinceLastTxSuccessHistogram.toProto(); 5662 linkProbeStats.successElapsedTimeMsHistogram = 5663 mLinkProbeSuccessElapsedTimeMsHistogram.toProto(); 5664 linkProbeStats.failureReasonCounts = mLinkProbeFailureReasonCounts.toProto( 5665 LinkProbeFailureReasonCount.class, 5666 (reason, count) -> { 5667 LinkProbeFailureReasonCount c = new LinkProbeFailureReasonCount(); 5668 c.failureReason = linkProbeFailureReasonToProto(reason); 5669 c.count = count; 5670 return c; 5671 }); 5672 linkProbeStats.experimentProbeCounts = mLinkProbeExperimentProbeCounts.toProto( 5673 ExperimentProbeCounts.class, 5674 (experimentId, probeCount) -> { 5675 ExperimentProbeCounts c = new ExperimentProbeCounts(); 5676 c.experimentId = experimentId; 5677 c.probeCount = probeCount; 5678 return c; 5679 }); 5680 mWifiLogProto.linkProbeStats = linkProbeStats; 5681 5682 mWifiLogProto.networkSelectionExperimentDecisionsList = 5683 makeNetworkSelectionExperimentDecisionsList(); 5684 5685 mWifiNetworkRequestApiLog.networkMatchSizeHistogram = 5686 mWifiNetworkRequestApiMatchSizeHistogram.toProto(); 5687 mWifiNetworkRequestApiLog.connectionDurationSecOnPrimaryIfaceHistogram = 5688 mWifiNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram.toProto(); 5689 mWifiNetworkRequestApiLog.connectionDurationSecOnSecondaryIfaceHistogram = 5690 mWifiNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram.toProto(); 5691 mWifiNetworkRequestApiLog.concurrentConnectionDurationSecHistogram = 5692 mWifiNetworkRequestApiConcurrentConnectionDurationSecHistogram.toProto(); 5693 mWifiLogProto.wifiNetworkRequestApiLog = mWifiNetworkRequestApiLog; 5694 5695 mWifiNetworkSuggestionApiLog.networkListSizeHistogram = 5696 mWifiNetworkSuggestionApiListSizeHistogram.toProto(); 5697 mWifiNetworkSuggestionApiLog.appCountPerType = 5698 mWifiNetworkSuggestionApiAppTypeCounter.toProto(SuggestionAppCount.class, 5699 (key, count) -> { 5700 SuggestionAppCount entry = new SuggestionAppCount(); 5701 entry.appType = key; 5702 entry.count = count; 5703 return entry; 5704 }); 5705 mWifiNetworkSuggestionApiLog.numPriorityGroups = 5706 mWifiNetworkSuggestionPriorityGroups.size(); 5707 mWifiNetworkSuggestionApiLog.numSavedNetworksWithConfiguredSuggestion = 5708 mWifiNetworkSuggestionCoexistSavedNetworks.size(); 5709 mWifiLogProto.wifiNetworkSuggestionApiLog = mWifiNetworkSuggestionApiLog; 5710 5711 UserReactionToApprovalUiEvent events = new UserReactionToApprovalUiEvent(); 5712 events.userApprovalAppUiReaction = mUserApprovalSuggestionAppUiReactionList 5713 .toArray(new UserReaction[0]); 5714 events.userApprovalCarrierUiReaction = mUserApprovalCarrierUiReactionList 5715 .toArray(new UserReaction[0]); 5716 mWifiLogProto.userReactionToApprovalUiEvent = events; 5717 5718 mWifiLockStats.highPerfLockAcqDurationSecHistogram = 5719 mWifiLockHighPerfAcqDurationSecHistogram.toProto(); 5720 5721 mWifiLockStats.lowLatencyLockAcqDurationSecHistogram = 5722 mWifiLockLowLatencyAcqDurationSecHistogram.toProto(); 5723 5724 mWifiLockStats.highPerfActiveSessionDurationSecHistogram = 5725 mWifiLockHighPerfActiveSessionDurationSecHistogram.toProto(); 5726 5727 mWifiLockStats.lowLatencyActiveSessionDurationSecHistogram = 5728 mWifiLockLowLatencyActiveSessionDurationSecHistogram.toProto(); 5729 5730 mWifiLogProto.wifiLockStats = mWifiLockStats; 5731 mWifiLogProto.wifiToggleStats = mWifiToggleStats; 5732 5733 /** 5734 * Convert the SparseIntArray of passpoint provision failure code 5735 * and counts to the proto's repeated IntKeyVal array. 5736 */ 5737 mWifiLogProto.passpointProvisionStats = new PasspointProvisionStats(); 5738 mWifiLogProto.passpointProvisionStats.numProvisionSuccess = mNumProvisionSuccess; 5739 mWifiLogProto.passpointProvisionStats.provisionFailureCount = 5740 mPasspointProvisionFailureCounts.toProto(ProvisionFailureCount.class, 5741 (key, count) -> { 5742 ProvisionFailureCount entry = new ProvisionFailureCount(); 5743 entry.failureCode = key; 5744 entry.count = count; 5745 return entry; 5746 }); 5747 // 'G' is due to that 1st Letter after _ becomes capital during protobuff compilation 5748 mWifiLogProto.txLinkSpeedCount2G = mTxLinkSpeedCount2g.toProto(); 5749 mWifiLogProto.txLinkSpeedCount5GLow = mTxLinkSpeedCount5gLow.toProto(); 5750 mWifiLogProto.txLinkSpeedCount5GMid = mTxLinkSpeedCount5gMid.toProto(); 5751 mWifiLogProto.txLinkSpeedCount5GHigh = mTxLinkSpeedCount5gHigh.toProto(); 5752 mWifiLogProto.txLinkSpeedCount6GLow = mTxLinkSpeedCount6gLow.toProto(); 5753 mWifiLogProto.txLinkSpeedCount6GMid = mTxLinkSpeedCount6gMid.toProto(); 5754 mWifiLogProto.txLinkSpeedCount6GHigh = mTxLinkSpeedCount6gHigh.toProto(); 5755 5756 mWifiLogProto.rxLinkSpeedCount2G = mRxLinkSpeedCount2g.toProto(); 5757 mWifiLogProto.rxLinkSpeedCount5GLow = mRxLinkSpeedCount5gLow.toProto(); 5758 mWifiLogProto.rxLinkSpeedCount5GMid = mRxLinkSpeedCount5gMid.toProto(); 5759 mWifiLogProto.rxLinkSpeedCount5GHigh = mRxLinkSpeedCount5gHigh.toProto(); 5760 mWifiLogProto.rxLinkSpeedCount6GLow = mRxLinkSpeedCount6gLow.toProto(); 5761 mWifiLogProto.rxLinkSpeedCount6GMid = mRxLinkSpeedCount6gMid.toProto(); 5762 mWifiLogProto.rxLinkSpeedCount6GHigh = mRxLinkSpeedCount6gHigh.toProto(); 5763 5764 HealthMonitorMetrics healthMonitorMetrics = mWifiHealthMonitor.buildProto(); 5765 if (healthMonitorMetrics != null) { 5766 mWifiLogProto.healthMonitorMetrics = healthMonitorMetrics; 5767 } 5768 mWifiLogProto.bssidBlocklistStats = mBssidBlocklistStats.toProto(); 5769 mWifiLogProto.connectionDurationStats = mConnectionDurationStats.toProto(); 5770 mWifiLogProto.wifiOffMetrics = mWifiOffMetrics.toProto(); 5771 mWifiLogProto.softApConfigLimitationMetrics = mSoftApConfigLimitationMetrics.toProto(); 5772 mWifiLogProto.channelUtilizationHistogram = 5773 new WifiMetricsProto.ChannelUtilizationHistogram(); 5774 mWifiLogProto.channelUtilizationHistogram.utilization2G = 5775 mChannelUtilizationHistogram2G.toProto(); 5776 mWifiLogProto.channelUtilizationHistogram.utilizationAbove2G = 5777 mChannelUtilizationHistogramAbove2G.toProto(); 5778 mWifiLogProto.throughputMbpsHistogram = 5779 new WifiMetricsProto.ThroughputMbpsHistogram(); 5780 mWifiLogProto.throughputMbpsHistogram.tx2G = 5781 mTxThroughputMbpsHistogram2G.toProto(); 5782 mWifiLogProto.throughputMbpsHistogram.txAbove2G = 5783 mTxThroughputMbpsHistogramAbove2G.toProto(); 5784 mWifiLogProto.throughputMbpsHistogram.rx2G = 5785 mRxThroughputMbpsHistogram2G.toProto(); 5786 mWifiLogProto.throughputMbpsHistogram.rxAbove2G = 5787 mRxThroughputMbpsHistogramAbove2G.toProto(); 5788 mWifiLogProto.meteredNetworkStatsSaved = mMeteredNetworkStatsBuilder.toProto(false); 5789 mWifiLogProto.meteredNetworkStatsSuggestion = mMeteredNetworkStatsBuilder.toProto(true); 5790 5791 InitPartialScanStats initialPartialScanStats = new InitPartialScanStats(); 5792 initialPartialScanStats.numScans = mInitPartialScanTotalCount; 5793 initialPartialScanStats.numSuccessScans = mInitPartialScanSuccessCount; 5794 initialPartialScanStats.numFailureScans = mInitPartialScanFailureCount; 5795 initialPartialScanStats.successfulScanChannelCountHistogram = 5796 mInitPartialScanSuccessHistogram.toProto(); 5797 initialPartialScanStats.failedScanChannelCountHistogram = 5798 mInitPartialScanFailureHistogram.toProto(); 5799 mWifiLogProto.initPartialScanStats = initialPartialScanStats; 5800 mWifiLogProto.carrierWifiMetrics = mCarrierWifiMetrics.toProto(); 5801 mWifiLogProto.mainlineModuleVersion = mWifiHealthMonitor.getWifiStackVersion(); 5802 mWifiLogProto.firstConnectAfterBootStats = mFirstConnectAfterBootStats; 5803 mWifiLogProto.wifiToWifiSwitchStats = buildWifiToWifiSwitchStats(); 5804 mWifiLogProto.bandwidthEstimatorStats = mWifiScoreCard.dumpBandwidthEstimatorStats(); 5805 mWifiLogProto.passpointDeauthImminentScope = mPasspointDeauthImminentScope.toProto(); 5806 mWifiLogProto.recentFailureAssociationStatus = 5807 mRecentFailureAssociationStatus.toProto(); 5808 } 5809 } 5810 buildWifiToWifiSwitchStats()5811 private WifiToWifiSwitchStats buildWifiToWifiSwitchStats() { 5812 mWifiToWifiSwitchStats.makeBeforeBreakLingerDurationSeconds = 5813 mMakeBeforeBreakLingeringDurationSeconds.toProto(); 5814 return mWifiToWifiSwitchStats; 5815 } 5816 linkProbeFailureReasonToProto(int reason)5817 private static int linkProbeFailureReasonToProto(int reason) { 5818 switch (reason) { 5819 case WifiNl80211Manager.SEND_MGMT_FRAME_ERROR_MCS_UNSUPPORTED: 5820 return LinkProbeStats.LINK_PROBE_FAILURE_REASON_MCS_UNSUPPORTED; 5821 case WifiNl80211Manager.SEND_MGMT_FRAME_ERROR_NO_ACK: 5822 return LinkProbeStats.LINK_PROBE_FAILURE_REASON_NO_ACK; 5823 case WifiNl80211Manager.SEND_MGMT_FRAME_ERROR_TIMEOUT: 5824 return LinkProbeStats.LINK_PROBE_FAILURE_REASON_TIMEOUT; 5825 case WifiNl80211Manager.SEND_MGMT_FRAME_ERROR_ALREADY_STARTED: 5826 return LinkProbeStats.LINK_PROBE_FAILURE_REASON_ALREADY_STARTED; 5827 default: 5828 return LinkProbeStats.LINK_PROBE_FAILURE_REASON_UNKNOWN; 5829 } 5830 } 5831 makeNetworkSelectionExperimentDecisionsList()5832 private NetworkSelectionExperimentDecisions[] makeNetworkSelectionExperimentDecisionsList() { 5833 NetworkSelectionExperimentDecisions[] results = new NetworkSelectionExperimentDecisions[ 5834 mNetworkSelectionExperimentPairNumChoicesCounts.size()]; 5835 int i = 0; 5836 for (Map.Entry<Pair<Integer, Integer>, NetworkSelectionExperimentResults> entry : 5837 mNetworkSelectionExperimentPairNumChoicesCounts.entrySet()) { 5838 NetworkSelectionExperimentDecisions result = new NetworkSelectionExperimentDecisions(); 5839 result.experiment1Id = entry.getKey().first; 5840 result.experiment2Id = entry.getKey().second; 5841 result.sameSelectionNumChoicesCounter = 5842 entry.getValue().sameSelectionNumChoicesCounter.toProto(); 5843 result.differentSelectionNumChoicesCounter = 5844 entry.getValue().differentSelectionNumChoicesCounter.toProto(); 5845 results[i] = result; 5846 i++; 5847 } 5848 return results; 5849 } 5850 5851 /** Sets the scoring experiment id to current value */ consolidateScoringParams()5852 private void consolidateScoringParams() { 5853 synchronized (mLock) { 5854 if (mScoringParams != null) { 5855 int experimentIdentifier = mScoringParams.getExperimentIdentifier(); 5856 if (experimentIdentifier == 0) { 5857 mWifiLogProto.scoreExperimentId = ""; 5858 } else { 5859 mWifiLogProto.scoreExperimentId = "x" + experimentIdentifier; 5860 } 5861 } 5862 } 5863 } 5864 makeNumConnectableNetworksBucketArray( SparseIntArray sia)5865 private WifiMetricsProto.NumConnectableNetworksBucket[] makeNumConnectableNetworksBucketArray( 5866 SparseIntArray sia) { 5867 WifiMetricsProto.NumConnectableNetworksBucket[] array = 5868 new WifiMetricsProto.NumConnectableNetworksBucket[sia.size()]; 5869 for (int i = 0; i < sia.size(); i++) { 5870 WifiMetricsProto.NumConnectableNetworksBucket keyVal = 5871 new WifiMetricsProto.NumConnectableNetworksBucket(); 5872 keyVal.numConnectableNetworks = sia.keyAt(i); 5873 keyVal.count = sia.valueAt(i); 5874 array[i] = keyVal; 5875 } 5876 return array; 5877 } 5878 5879 private WifiMetricsProto.WifiConfigStoreIO.DurationBucket[] makeWifiConfigStoreIODurationBucketArray(SparseIntArray sia)5880 makeWifiConfigStoreIODurationBucketArray(SparseIntArray sia) { 5881 MetricsUtils.GenericBucket[] genericBuckets = 5882 MetricsUtils.linearHistogramToGenericBuckets(sia, 5883 WIFI_CONFIG_STORE_IO_DURATION_BUCKET_RANGES_MS); 5884 WifiMetricsProto.WifiConfigStoreIO.DurationBucket[] array = 5885 new WifiMetricsProto.WifiConfigStoreIO.DurationBucket[genericBuckets.length]; 5886 try { 5887 for (int i = 0; i < genericBuckets.length; i++) { 5888 array[i] = new WifiMetricsProto.WifiConfigStoreIO.DurationBucket(); 5889 array[i].rangeStartMs = toIntExact(genericBuckets[i].start); 5890 array[i].rangeEndMs = toIntExact(genericBuckets[i].end); 5891 array[i].count = genericBuckets[i].count; 5892 } 5893 } catch (ArithmeticException e) { 5894 // Return empty array on any overflow errors. 5895 array = new WifiMetricsProto.WifiConfigStoreIO.DurationBucket[0]; 5896 } 5897 return array; 5898 } 5899 5900 /** 5901 * Clear all WifiMetrics, except for currentConnectionEvent and Open Network Notification 5902 * feature enabled state, blocklist size. 5903 */ clear()5904 private void clear() { 5905 synchronized (mLock) { 5906 mConnectionEventList.clear(); 5907 // Add in-progress events back 5908 mConnectionEventList.addAll(mCurrentConnectionEventPerIface.values()); 5909 5910 mScanReturnEntries.clear(); 5911 mWifiSystemStateEntries.clear(); 5912 mRecordStartTimeSec = mClock.getElapsedSinceBootMillis() / 1000; 5913 mRssiPollCountsMap.clear(); 5914 mRssiDeltaCounts.clear(); 5915 mLinkSpeedCounts.clear(); 5916 mTxLinkSpeedCount2g.clear(); 5917 mTxLinkSpeedCount5gLow.clear(); 5918 mTxLinkSpeedCount5gMid.clear(); 5919 mTxLinkSpeedCount5gHigh.clear(); 5920 mTxLinkSpeedCount6gLow.clear(); 5921 mTxLinkSpeedCount6gMid.clear(); 5922 mTxLinkSpeedCount6gHigh.clear(); 5923 mRxLinkSpeedCount2g.clear(); 5924 mRxLinkSpeedCount5gLow.clear(); 5925 mRxLinkSpeedCount5gMid.clear(); 5926 mRxLinkSpeedCount5gHigh.clear(); 5927 mRxLinkSpeedCount6gLow.clear(); 5928 mRxLinkSpeedCount6gMid.clear(); 5929 mRxLinkSpeedCount6gHigh.clear(); 5930 mWifiAlertReasonCounts.clear(); 5931 mMakeBeforeBreakLingeringDurationSeconds.clear(); 5932 mWifiScoreCounts.clear(); 5933 mWifiUsabilityScoreCounts.clear(); 5934 mWifiLogProto.clear(); 5935 mScanResultRssiTimestampMillis = -1; 5936 mSoftApManagerReturnCodeCounts.clear(); 5937 mStaEventList.clear(); 5938 mUserActionEventList.clear(); 5939 mWifiAwareMetrics.clear(); 5940 mRttMetrics.clear(); 5941 mTotalSsidsInScanHistogram.clear(); 5942 mTotalBssidsInScanHistogram.clear(); 5943 mAvailableOpenSsidsInScanHistogram.clear(); 5944 mAvailableOpenBssidsInScanHistogram.clear(); 5945 mAvailableSavedSsidsInScanHistogram.clear(); 5946 mAvailableSavedBssidsInScanHistogram.clear(); 5947 mAvailableOpenOrSavedSsidsInScanHistogram.clear(); 5948 mAvailableOpenOrSavedBssidsInScanHistogram.clear(); 5949 mAvailableSavedPasspointProviderProfilesInScanHistogram.clear(); 5950 mAvailableSavedPasspointProviderBssidsInScanHistogram.clear(); 5951 mPnoScanMetrics.clear(); 5952 mWifiLinkLayerUsageStats.clear(); 5953 mRadioStats.clear(); 5954 mConnectToNetworkNotificationCount.clear(); 5955 mConnectToNetworkNotificationActionCount.clear(); 5956 mNumOpenNetworkRecommendationUpdates = 0; 5957 mNumOpenNetworkConnectMessageFailedToSend = 0; 5958 mObservedHotspotR1ApInScanHistogram.clear(); 5959 mObservedHotspotR2ApInScanHistogram.clear(); 5960 mObservedHotspotR3ApInScanHistogram.clear(); 5961 mObservedHotspotR1EssInScanHistogram.clear(); 5962 mObservedHotspotR2EssInScanHistogram.clear(); 5963 mObservedHotspotR3EssInScanHistogram.clear(); 5964 mObservedHotspotR1ApsPerEssInScanHistogram.clear(); 5965 mObservedHotspotR2ApsPerEssInScanHistogram.clear(); 5966 mObservedHotspotR3ApsPerEssInScanHistogram.clear(); 5967 mSoftApEventListTethered.clear(); 5968 mSoftApEventListLocalOnly.clear(); 5969 mWifiWakeMetrics.clear(); 5970 mObserved80211mcApInScanHistogram.clear(); 5971 mWifiIsUnusableList.clear(); 5972 mInstalledPasspointProfileTypeForR1.clear(); 5973 mInstalledPasspointProfileTypeForR2.clear(); 5974 mWifiUsabilityStatsListGood.clear(); 5975 mWifiUsabilityStatsListBad.clear(); 5976 mWifiUsabilityStatsEntriesList.clear(); 5977 mMobilityStatePnoStatsMap.clear(); 5978 mWifiP2pMetrics.clear(); 5979 mDppMetrics.clear(); 5980 mWifiUsabilityStatsCounter = 0; 5981 mLastBssid = null; 5982 mLastFrequency = -1; 5983 mSeqNumInsideFramework = 0; 5984 mLastWifiUsabilityScore = -1; 5985 mLastWifiUsabilityScoreNoReset = -1; 5986 mLastPredictionHorizonSec = -1; 5987 mLastPredictionHorizonSecNoReset = -1; 5988 mSeqNumToFramework = -1; 5989 mProbeStatusSinceLastUpdate = 5990 android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE; 5991 mProbeElapsedTimeSinceLastUpdateMs = -1; 5992 mProbeMcsRateSinceLastUpdate = -1; 5993 mScoreBreachLowTimeMillis = -1; 5994 mMeteredNetworkStatsBuilder.clear(); 5995 mWifiConfigStoreReadDurationHistogram.clear(); 5996 mWifiConfigStoreWriteDurationHistogram.clear(); 5997 mLinkProbeSuccessRssiCounts.clear(); 5998 mLinkProbeFailureRssiCounts.clear(); 5999 mLinkProbeSuccessLinkSpeedCounts.clear(); 6000 mLinkProbeFailureLinkSpeedCounts.clear(); 6001 mLinkProbeSuccessSecondsSinceLastTxSuccessHistogram.clear(); 6002 mLinkProbeFailureSecondsSinceLastTxSuccessHistogram.clear(); 6003 mLinkProbeSuccessElapsedTimeMsHistogram.clear(); 6004 mLinkProbeFailureReasonCounts.clear(); 6005 mLinkProbeExperimentProbeCounts.clear(); 6006 mLinkProbeStaEventCount = 0; 6007 mNetworkSelectionExperimentPairNumChoicesCounts.clear(); 6008 mWifiNetworkSuggestionApiLog.clear(); 6009 mWifiNetworkRequestApiMatchSizeHistogram.clear(); 6010 mWifiNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram.clear(); 6011 mWifiNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram.clear(); 6012 mWifiNetworkRequestApiConcurrentConnectionDurationSecHistogram.clear(); 6013 mWifiNetworkSuggestionApiListSizeHistogram.clear(); 6014 mWifiNetworkSuggestionApiAppTypeCounter.clear(); 6015 mUserApprovalSuggestionAppUiReactionList.clear(); 6016 mUserApprovalCarrierUiReactionList.clear(); 6017 mWifiLockHighPerfAcqDurationSecHistogram.clear(); 6018 mWifiLockLowLatencyAcqDurationSecHistogram.clear(); 6019 mWifiLockHighPerfActiveSessionDurationSecHistogram.clear(); 6020 mWifiLockLowLatencyActiveSessionDurationSecHistogram.clear(); 6021 mWifiLockStats.clear(); 6022 mWifiToggleStats.clear(); 6023 mChannelUtilizationHistogram2G.clear(); 6024 mChannelUtilizationHistogramAbove2G.clear(); 6025 mTxThroughputMbpsHistogram2G.clear(); 6026 mRxThroughputMbpsHistogram2G.clear(); 6027 mTxThroughputMbpsHistogramAbove2G.clear(); 6028 mRxThroughputMbpsHistogramAbove2G.clear(); 6029 mPasspointProvisionFailureCounts.clear(); 6030 mNumProvisionSuccess = 0; 6031 mBssidBlocklistStats = new BssidBlocklistStats(); 6032 mConnectionDurationStats.clear(); 6033 mWifiOffMetrics.clear(); 6034 mSoftApConfigLimitationMetrics.clear(); 6035 //Initial partial scan metrics 6036 mInitPartialScanTotalCount = 0; 6037 mInitPartialScanSuccessCount = 0; 6038 mInitPartialScanFailureCount = 0; 6039 mInitPartialScanSuccessHistogram.clear(); 6040 mInitPartialScanFailureHistogram.clear(); 6041 mCarrierWifiMetrics.clear(); 6042 mFirstConnectAfterBootStats = null; 6043 mWifiToWifiSwitchStats.clear(); 6044 mPasspointDeauthImminentScope.clear(); 6045 mRecentFailureAssociationStatus.clear(); 6046 mWifiNetworkSuggestionPriorityGroups.clear(); 6047 mWifiNetworkSuggestionCoexistSavedNetworks.clear(); 6048 } 6049 } 6050 6051 /** 6052 * Set screen state (On/Off) 6053 */ setScreenState(boolean screenOn)6054 private void setScreenState(boolean screenOn) { 6055 synchronized (mLock) { 6056 mScreenOn = screenOn; 6057 } 6058 } 6059 isPrimary(String ifaceName)6060 private boolean isPrimary(String ifaceName) { 6061 return mIfaceToRoleMap.get(ifaceName) == ActiveModeManager.ROLE_CLIENT_PRIMARY; 6062 } 6063 6064 /** 6065 * Set wifi state (WIFI_UNKNOWN, WIFI_DISABLED, WIFI_DISCONNECTED, WIFI_ASSOCIATED) 6066 */ setWifiState(String ifaceName, int wifiState)6067 public void setWifiState(String ifaceName, int wifiState) { 6068 synchronized (mLock) { 6069 mWifiState = wifiState; 6070 // set wifi priority over setting when any STA gets connected. 6071 if (wifiState == WifiMetricsProto.WifiLog.WIFI_ASSOCIATED) { 6072 mWifiWins = true; 6073 mWifiWinsUsabilityScore = true; 6074 } 6075 if (isPrimary(ifaceName) && (wifiState == WifiMetricsProto.WifiLog.WIFI_DISCONNECTED 6076 || wifiState == WifiMetricsProto.WifiLog.WIFI_DISABLED)) { 6077 mWifiStatusBuilder = new WifiStatusBuilder(); 6078 } 6079 } 6080 } 6081 6082 /** 6083 * Message handler for interesting WifiMonitor messages. Generates StaEvents 6084 */ processMessage(Message msg)6085 private void processMessage(Message msg) { 6086 String ifaceName = msg.getData().getString(WifiMonitor.KEY_IFACE); 6087 6088 StaEvent event = new StaEvent(); 6089 boolean logEvent = true; 6090 switch (msg.what) { 6091 case WifiMonitor.ASSOCIATION_REJECTION_EVENT: 6092 event.type = StaEvent.TYPE_ASSOCIATION_REJECTION_EVENT; 6093 AssocRejectEventInfo assocRejectEventInfo = (AssocRejectEventInfo) msg.obj; 6094 event.associationTimedOut = assocRejectEventInfo.timedOut; 6095 event.status = assocRejectEventInfo.statusCode; 6096 break; 6097 case WifiMonitor.AUTHENTICATION_FAILURE_EVENT: 6098 event.type = StaEvent.TYPE_AUTHENTICATION_FAILURE_EVENT; 6099 AuthenticationFailureEventInfo authenticationFailureEventInfo = 6100 (AuthenticationFailureEventInfo) msg.obj; 6101 switch (authenticationFailureEventInfo.reasonCode) { 6102 case WifiManager.ERROR_AUTH_FAILURE_NONE: 6103 event.authFailureReason = StaEvent.AUTH_FAILURE_NONE; 6104 break; 6105 case WifiManager.ERROR_AUTH_FAILURE_TIMEOUT: 6106 event.authFailureReason = StaEvent.AUTH_FAILURE_TIMEOUT; 6107 break; 6108 case WifiManager.ERROR_AUTH_FAILURE_WRONG_PSWD: 6109 event.authFailureReason = StaEvent.AUTH_FAILURE_WRONG_PSWD; 6110 break; 6111 case WifiManager.ERROR_AUTH_FAILURE_EAP_FAILURE: 6112 event.authFailureReason = StaEvent.AUTH_FAILURE_EAP_FAILURE; 6113 break; 6114 default: 6115 break; 6116 } 6117 break; 6118 case WifiMonitor.NETWORK_CONNECTION_EVENT: 6119 event.type = StaEvent.TYPE_NETWORK_CONNECTION_EVENT; 6120 break; 6121 case WifiMonitor.NETWORK_DISCONNECTION_EVENT: 6122 event.type = StaEvent.TYPE_NETWORK_DISCONNECTION_EVENT; 6123 DisconnectEventInfo disconnectEventInfo = (DisconnectEventInfo) msg.obj; 6124 event.reason = disconnectEventInfo.reasonCode; 6125 event.localGen = disconnectEventInfo.locallyGenerated; 6126 break; 6127 case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT: 6128 logEvent = false; 6129 StateChangeResult stateChangeResult = (StateChangeResult) msg.obj; 6130 mSupplicantStateChangeBitmask |= supplicantStateToBit(stateChangeResult.state); 6131 break; 6132 case WifiMonitor.ASSOCIATED_BSSID_EVENT: 6133 event.type = StaEvent.TYPE_CMD_ASSOCIATED_BSSID; 6134 break; 6135 case WifiMonitor.TARGET_BSSID_EVENT: 6136 event.type = StaEvent.TYPE_CMD_TARGET_BSSID; 6137 break; 6138 default: 6139 return; 6140 } 6141 if (logEvent) { 6142 addStaEvent(ifaceName, event); 6143 } 6144 } 6145 /** 6146 * Log a StaEvent from ClientModeImpl. The StaEvent must not be one of the supplicant 6147 * generated event types, which are logged through 'sendMessage' 6148 * @param type StaEvent.EventType describing the event 6149 */ logStaEvent(String ifaceName, int type)6150 public void logStaEvent(String ifaceName, int type) { 6151 logStaEvent(ifaceName, type, StaEvent.DISCONNECT_UNKNOWN, null); 6152 } 6153 /** 6154 * Log a StaEvent from ClientModeImpl. The StaEvent must not be one of the supplicant 6155 * generated event types, which are logged through 'sendMessage' 6156 * @param type StaEvent.EventType describing the event 6157 * @param config WifiConfiguration for a framework initiated connection attempt 6158 */ logStaEvent(String ifaceName, int type, WifiConfiguration config)6159 public void logStaEvent(String ifaceName, int type, WifiConfiguration config) { 6160 logStaEvent(ifaceName, type, StaEvent.DISCONNECT_UNKNOWN, config); 6161 } 6162 /** 6163 * Log a StaEvent from ClientModeImpl. The StaEvent must not be one of the supplicant 6164 * generated event types, which are logged through 'sendMessage' 6165 * @param type StaEvent.EventType describing the event 6166 * @param frameworkDisconnectReason StaEvent.FrameworkDisconnectReason explaining why framework 6167 * initiated a FRAMEWORK_DISCONNECT 6168 */ logStaEvent(String ifaceName, int type, int frameworkDisconnectReason)6169 public void logStaEvent(String ifaceName, int type, int frameworkDisconnectReason) { 6170 logStaEvent(ifaceName, type, frameworkDisconnectReason, null); 6171 } 6172 /** 6173 * Log a StaEvent from ClientModeImpl. The StaEvent must not be one of the supplicant 6174 * generated event types, which are logged through 'sendMessage' 6175 * @param type StaEvent.EventType describing the event 6176 * @param frameworkDisconnectReason StaEvent.FrameworkDisconnectReason explaining why framework 6177 * initiated a FRAMEWORK_DISCONNECT 6178 * @param config WifiConfiguration for a framework initiated connection attempt 6179 */ logStaEvent(String ifaceName, int type, int frameworkDisconnectReason, WifiConfiguration config)6180 public void logStaEvent(String ifaceName, int type, int frameworkDisconnectReason, 6181 WifiConfiguration config) { 6182 switch (type) { 6183 case StaEvent.TYPE_CMD_START_ROAM: 6184 ConnectionEvent currentConnectionEvent = mCurrentConnectionEventPerIface.get( 6185 ifaceName); 6186 if (currentConnectionEvent != null) { 6187 currentConnectionEvent.mRouterFingerPrint.mIsFrameworkInitiatedRoaming = true; 6188 } 6189 break; 6190 case StaEvent.TYPE_CMD_IP_CONFIGURATION_SUCCESSFUL: 6191 case StaEvent.TYPE_CMD_IP_CONFIGURATION_LOST: 6192 case StaEvent.TYPE_CMD_IP_REACHABILITY_LOST: 6193 case StaEvent.TYPE_CMD_START_CONNECT: 6194 case StaEvent.TYPE_CONNECT_NETWORK: 6195 break; 6196 case StaEvent.TYPE_NETWORK_AGENT_VALID_NETWORK: 6197 mWifiStatusBuilder.setValidated(true); 6198 break; 6199 case StaEvent.TYPE_FRAMEWORK_DISCONNECT: 6200 case StaEvent.TYPE_SCORE_BREACH: 6201 case StaEvent.TYPE_MAC_CHANGE: 6202 case StaEvent.TYPE_WIFI_ENABLED: 6203 case StaEvent.TYPE_WIFI_DISABLED: 6204 case StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH: 6205 break; 6206 default: 6207 Log.e(TAG, "Unknown StaEvent:" + type); 6208 return; 6209 } 6210 StaEvent event = new StaEvent(); 6211 event.type = type; 6212 if (frameworkDisconnectReason != StaEvent.DISCONNECT_UNKNOWN) { 6213 event.frameworkDisconnectReason = frameworkDisconnectReason; 6214 } 6215 event.configInfo = createConfigInfo(config); 6216 addStaEvent(ifaceName, event); 6217 } 6218 addStaEvent(String ifaceName, StaEvent staEvent)6219 private void addStaEvent(String ifaceName, StaEvent staEvent) { 6220 // Nano proto runtime will throw a NPE during serialization if interfaceName is null 6221 if (ifaceName == null) { 6222 // Check if any ConcreteClientModeManager's role is switching to ROLE_CLIENT_PRIMARY 6223 ConcreteClientModeManager targetConcreteClientModeManager = 6224 mActiveModeWarden.getClientModeManagerTransitioningIntoRole( 6225 ROLE_CLIENT_PRIMARY); 6226 if (targetConcreteClientModeManager == null) { 6227 Log.wtf(TAG, "Null StaEvent.ifaceName: " + staEventToString(staEvent)); 6228 } 6229 return; 6230 } 6231 staEvent.interfaceName = ifaceName; 6232 staEvent.interfaceRole = convertIfaceToEnum(ifaceName); 6233 staEvent.startTimeMillis = mClock.getElapsedSinceBootMillis(); 6234 staEvent.lastRssi = mLastPollRssi; 6235 staEvent.lastFreq = mLastPollFreq; 6236 staEvent.lastLinkSpeed = mLastPollLinkSpeed; 6237 staEvent.supplicantStateChangesBitmask = mSupplicantStateChangeBitmask; 6238 staEvent.lastScore = mLastScore; 6239 staEvent.lastWifiUsabilityScore = mLastWifiUsabilityScore; 6240 staEvent.lastPredictionHorizonSec = mLastPredictionHorizonSec; 6241 staEvent.mobileTxBytes = mFacade.getMobileTxBytes(); 6242 staEvent.mobileRxBytes = mFacade.getMobileRxBytes(); 6243 staEvent.totalTxBytes = mFacade.getTotalTxBytes(); 6244 staEvent.totalRxBytes = mFacade.getTotalRxBytes(); 6245 staEvent.screenOn = mScreenOn; 6246 if (mWifiDataStall != null) { 6247 staEvent.isCellularDataAvailable = mWifiDataStall.isCellularDataAvailable(); 6248 } 6249 staEvent.isAdaptiveConnectivityEnabled = mAdaptiveConnectivityEnabled; 6250 mSupplicantStateChangeBitmask = 0; 6251 mLastPollRssi = -127; 6252 mLastPollFreq = -1; 6253 mLastPollLinkSpeed = -1; 6254 mLastPollRxLinkSpeed = -1; 6255 mLastScore = -1; 6256 mLastWifiUsabilityScore = -1; 6257 mLastPredictionHorizonSec = -1; 6258 synchronized (mLock) { 6259 mStaEventList.add(new StaEventWithTime(staEvent, mClock.getWallClockMillis())); 6260 // Prune StaEventList if it gets too long 6261 if (mStaEventList.size() > MAX_STA_EVENTS) mStaEventList.remove(); 6262 } 6263 } 6264 createConfigInfo(WifiConfiguration config)6265 private ConfigInfo createConfigInfo(WifiConfiguration config) { 6266 if (config == null) return null; 6267 ConfigInfo info = new ConfigInfo(); 6268 info.allowedKeyManagement = bitSetToInt(config.allowedKeyManagement); 6269 info.allowedProtocols = bitSetToInt(config.allowedProtocols); 6270 info.allowedAuthAlgorithms = bitSetToInt(config.allowedAuthAlgorithms); 6271 info.allowedPairwiseCiphers = bitSetToInt(config.allowedPairwiseCiphers); 6272 info.allowedGroupCiphers = bitSetToInt(config.allowedGroupCiphers); 6273 info.hiddenSsid = config.hiddenSSID; 6274 info.isPasspoint = config.isPasspoint(); 6275 info.isEphemeral = config.isEphemeral(); 6276 info.hasEverConnected = config.getNetworkSelectionStatus().hasEverConnected(); 6277 ScanResult candidate = config.getNetworkSelectionStatus().getCandidate(); 6278 if (candidate != null) { 6279 info.scanRssi = candidate.level; 6280 info.scanFreq = candidate.frequency; 6281 } 6282 return info; 6283 } 6284 6285 private static final int[] WIFI_MONITOR_EVENTS = { 6286 WifiMonitor.ASSOCIATION_REJECTION_EVENT, 6287 WifiMonitor.AUTHENTICATION_FAILURE_EVENT, 6288 WifiMonitor.NETWORK_CONNECTION_EVENT, 6289 WifiMonitor.NETWORK_DISCONNECTION_EVENT, 6290 WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT, 6291 WifiMonitor.ASSOCIATED_BSSID_EVENT, 6292 WifiMonitor.TARGET_BSSID_EVENT, 6293 }; 6294 registerForWifiMonitorEvents(String ifaceName)6295 public void registerForWifiMonitorEvents(String ifaceName) { 6296 for (int event : WIFI_MONITOR_EVENTS) { 6297 mWifiMonitor.registerHandler(ifaceName, event, mHandler); 6298 } 6299 } 6300 deregisterForWifiMonitorEvents(String ifaceName)6301 public void deregisterForWifiMonitorEvents(String ifaceName) { 6302 for (int event : WIFI_MONITOR_EVENTS) { 6303 mWifiMonitor.deregisterHandler(ifaceName, event, mHandler); 6304 } 6305 } 6306 getWifiAwareMetrics()6307 public WifiAwareMetrics getWifiAwareMetrics() { 6308 return mWifiAwareMetrics; 6309 } 6310 getWakeupMetrics()6311 public WifiWakeMetrics getWakeupMetrics() { 6312 return mWifiWakeMetrics; 6313 } 6314 getRttMetrics()6315 public RttMetrics getRttMetrics() { 6316 return mRttMetrics; 6317 } 6318 6319 // Rather than generate a StaEvent for each SUPPLICANT_STATE_CHANGE, cache these in a bitmask 6320 // and attach it to the next event which is generated. 6321 private int mSupplicantStateChangeBitmask = 0; 6322 6323 /** 6324 * Converts a SupplicantState value to a single bit, with position defined by 6325 * {@code StaEvent.SupplicantState} 6326 */ supplicantStateToBit(SupplicantState state)6327 public static int supplicantStateToBit(SupplicantState state) { 6328 switch(state) { 6329 case DISCONNECTED: 6330 return 1 << StaEvent.STATE_DISCONNECTED; 6331 case INTERFACE_DISABLED: 6332 return 1 << StaEvent.STATE_INTERFACE_DISABLED; 6333 case INACTIVE: 6334 return 1 << StaEvent.STATE_INACTIVE; 6335 case SCANNING: 6336 return 1 << StaEvent.STATE_SCANNING; 6337 case AUTHENTICATING: 6338 return 1 << StaEvent.STATE_AUTHENTICATING; 6339 case ASSOCIATING: 6340 return 1 << StaEvent.STATE_ASSOCIATING; 6341 case ASSOCIATED: 6342 return 1 << StaEvent.STATE_ASSOCIATED; 6343 case FOUR_WAY_HANDSHAKE: 6344 return 1 << StaEvent.STATE_FOUR_WAY_HANDSHAKE; 6345 case GROUP_HANDSHAKE: 6346 return 1 << StaEvent.STATE_GROUP_HANDSHAKE; 6347 case COMPLETED: 6348 return 1 << StaEvent.STATE_COMPLETED; 6349 case DORMANT: 6350 return 1 << StaEvent.STATE_DORMANT; 6351 case UNINITIALIZED: 6352 return 1 << StaEvent.STATE_UNINITIALIZED; 6353 case INVALID: 6354 return 1 << StaEvent.STATE_INVALID; 6355 default: 6356 Log.wtf(TAG, "Got unknown supplicant state: " + state.ordinal()); 6357 return 0; 6358 } 6359 } 6360 supplicantStateChangesBitmaskToString(int mask)6361 private static String supplicantStateChangesBitmaskToString(int mask) { 6362 StringBuilder sb = new StringBuilder(); 6363 sb.append("supplicantStateChangeEvents: {"); 6364 if ((mask & (1 << StaEvent.STATE_DISCONNECTED)) > 0) sb.append(" DISCONNECTED"); 6365 if ((mask & (1 << StaEvent.STATE_INTERFACE_DISABLED)) > 0) sb.append(" INTERFACE_DISABLED"); 6366 if ((mask & (1 << StaEvent.STATE_INACTIVE)) > 0) sb.append(" INACTIVE"); 6367 if ((mask & (1 << StaEvent.STATE_SCANNING)) > 0) sb.append(" SCANNING"); 6368 if ((mask & (1 << StaEvent.STATE_AUTHENTICATING)) > 0) sb.append(" AUTHENTICATING"); 6369 if ((mask & (1 << StaEvent.STATE_ASSOCIATING)) > 0) sb.append(" ASSOCIATING"); 6370 if ((mask & (1 << StaEvent.STATE_ASSOCIATED)) > 0) sb.append(" ASSOCIATED"); 6371 if ((mask & (1 << StaEvent.STATE_FOUR_WAY_HANDSHAKE)) > 0) sb.append(" FOUR_WAY_HANDSHAKE"); 6372 if ((mask & (1 << StaEvent.STATE_GROUP_HANDSHAKE)) > 0) sb.append(" GROUP_HANDSHAKE"); 6373 if ((mask & (1 << StaEvent.STATE_COMPLETED)) > 0) sb.append(" COMPLETED"); 6374 if ((mask & (1 << StaEvent.STATE_DORMANT)) > 0) sb.append(" DORMANT"); 6375 if ((mask & (1 << StaEvent.STATE_UNINITIALIZED)) > 0) sb.append(" UNINITIALIZED"); 6376 if ((mask & (1 << StaEvent.STATE_INVALID)) > 0) sb.append(" INVALID"); 6377 sb.append(" }"); 6378 return sb.toString(); 6379 } 6380 6381 /** 6382 * Returns a human readable string from a Sta Event. Only adds information relevant to the event 6383 * type. 6384 */ staEventToString(StaEvent event)6385 public static String staEventToString(StaEvent event) { 6386 if (event == null) return "<NULL>"; 6387 StringBuilder sb = new StringBuilder(); 6388 switch (event.type) { 6389 case StaEvent.TYPE_ASSOCIATION_REJECTION_EVENT: 6390 sb.append("ASSOCIATION_REJECTION_EVENT") 6391 .append(" timedOut=").append(event.associationTimedOut) 6392 .append(" status=").append(event.status).append(":") 6393 .append(StaIfaceStatusCode.toString(event.status)); 6394 break; 6395 case StaEvent.TYPE_AUTHENTICATION_FAILURE_EVENT: 6396 sb.append("AUTHENTICATION_FAILURE_EVENT reason=").append(event.authFailureReason) 6397 .append(":").append(authFailureReasonToString(event.authFailureReason)); 6398 break; 6399 case StaEvent.TYPE_NETWORK_CONNECTION_EVENT: 6400 sb.append("NETWORK_CONNECTION_EVENT"); 6401 break; 6402 case StaEvent.TYPE_NETWORK_DISCONNECTION_EVENT: 6403 sb.append("NETWORK_DISCONNECTION_EVENT") 6404 .append(" local_gen=").append(event.localGen) 6405 .append(" reason=").append(event.reason).append(":") 6406 .append(StaIfaceReasonCode.toString( 6407 (event.reason >= 0 ? event.reason : -1 * event.reason))); 6408 break; 6409 case StaEvent.TYPE_CMD_ASSOCIATED_BSSID: 6410 sb.append("CMD_ASSOCIATED_BSSID"); 6411 break; 6412 case StaEvent.TYPE_CMD_IP_CONFIGURATION_SUCCESSFUL: 6413 sb.append("CMD_IP_CONFIGURATION_SUCCESSFUL"); 6414 break; 6415 case StaEvent.TYPE_CMD_IP_CONFIGURATION_LOST: 6416 sb.append("CMD_IP_CONFIGURATION_LOST"); 6417 break; 6418 case StaEvent.TYPE_CMD_IP_REACHABILITY_LOST: 6419 sb.append("CMD_IP_REACHABILITY_LOST"); 6420 break; 6421 case StaEvent.TYPE_CMD_TARGET_BSSID: 6422 sb.append("CMD_TARGET_BSSID"); 6423 break; 6424 case StaEvent.TYPE_CMD_START_CONNECT: 6425 sb.append("CMD_START_CONNECT"); 6426 break; 6427 case StaEvent.TYPE_CMD_START_ROAM: 6428 sb.append("CMD_START_ROAM"); 6429 break; 6430 case StaEvent.TYPE_CONNECT_NETWORK: 6431 sb.append("CONNECT_NETWORK"); 6432 break; 6433 case StaEvent.TYPE_NETWORK_AGENT_VALID_NETWORK: 6434 sb.append("NETWORK_AGENT_VALID_NETWORK"); 6435 break; 6436 case StaEvent.TYPE_FRAMEWORK_DISCONNECT: 6437 sb.append("FRAMEWORK_DISCONNECT") 6438 .append(" reason=") 6439 .append(frameworkDisconnectReasonToString(event.frameworkDisconnectReason)); 6440 break; 6441 case StaEvent.TYPE_SCORE_BREACH: 6442 sb.append("SCORE_BREACH"); 6443 break; 6444 case StaEvent.TYPE_MAC_CHANGE: 6445 sb.append("MAC_CHANGE"); 6446 break; 6447 case StaEvent.TYPE_WIFI_ENABLED: 6448 sb.append("WIFI_ENABLED"); 6449 break; 6450 case StaEvent.TYPE_WIFI_DISABLED: 6451 sb.append("WIFI_DISABLED"); 6452 break; 6453 case StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH: 6454 sb.append("WIFI_USABILITY_SCORE_BREACH"); 6455 break; 6456 case StaEvent.TYPE_LINK_PROBE: 6457 sb.append("LINK_PROBE"); 6458 sb.append(" linkProbeWasSuccess=").append(event.linkProbeWasSuccess); 6459 if (event.linkProbeWasSuccess) { 6460 sb.append(" linkProbeSuccessElapsedTimeMs=") 6461 .append(event.linkProbeSuccessElapsedTimeMs); 6462 } else { 6463 sb.append(" linkProbeFailureReason=").append(event.linkProbeFailureReason); 6464 } 6465 break; 6466 default: 6467 sb.append("UNKNOWN " + event.type + ":"); 6468 break; 6469 } 6470 if (event.lastRssi != -127) sb.append(" lastRssi=").append(event.lastRssi); 6471 if (event.lastFreq != -1) sb.append(" lastFreq=").append(event.lastFreq); 6472 if (event.lastLinkSpeed != -1) sb.append(" lastLinkSpeed=").append(event.lastLinkSpeed); 6473 if (event.lastScore != -1) sb.append(" lastScore=").append(event.lastScore); 6474 if (event.lastWifiUsabilityScore != -1) { 6475 sb.append(" lastWifiUsabilityScore=").append(event.lastWifiUsabilityScore); 6476 sb.append(" lastPredictionHorizonSec=").append(event.lastPredictionHorizonSec); 6477 } 6478 sb.append(" screenOn=").append(event.screenOn); 6479 sb.append(" cellularData=").append(event.isCellularDataAvailable); 6480 sb.append(" adaptiveConnectivity=").append(event.isAdaptiveConnectivityEnabled); 6481 if (event.supplicantStateChangesBitmask != 0) { 6482 sb.append(", ").append(supplicantStateChangesBitmaskToString( 6483 event.supplicantStateChangesBitmask)); 6484 } 6485 if (event.configInfo != null) { 6486 sb.append(", ").append(configInfoToString(event.configInfo)); 6487 } 6488 if (event.mobileTxBytes > 0) sb.append(" mobileTxBytes=").append(event.mobileTxBytes); 6489 if (event.mobileRxBytes > 0) sb.append(" mobileRxBytes=").append(event.mobileRxBytes); 6490 if (event.totalTxBytes > 0) sb.append(" totalTxBytes=").append(event.totalTxBytes); 6491 if (event.totalRxBytes > 0) sb.append(" totalRxBytes=").append(event.totalRxBytes); 6492 sb.append(" interfaceName=").append(event.interfaceName); 6493 sb.append(" interfaceRole=").append(clientRoleEnumToString(event.interfaceRole)); 6494 return sb.toString(); 6495 } 6496 convertIfaceToEnum(String ifaceName)6497 private int convertIfaceToEnum(String ifaceName) { 6498 ActiveModeManager.ClientRole role = mIfaceToRoleMap.get(ifaceName); 6499 if (role == ActiveModeManager.ROLE_CLIENT_SCAN_ONLY) { 6500 return WifiMetricsProto.ROLE_CLIENT_SCAN_ONLY; 6501 } else if (role == ActiveModeManager.ROLE_CLIENT_SECONDARY_TRANSIENT) { 6502 return WifiMetricsProto.ROLE_CLIENT_SECONDARY_TRANSIENT; 6503 } else if (role == ActiveModeManager.ROLE_CLIENT_LOCAL_ONLY) { 6504 return WifiMetricsProto.ROLE_CLIENT_LOCAL_ONLY; 6505 } else if (role == ActiveModeManager.ROLE_CLIENT_PRIMARY) { 6506 return WifiMetricsProto.ROLE_CLIENT_PRIMARY; 6507 } else if (role == ActiveModeManager.ROLE_CLIENT_SECONDARY_LONG_LIVED) { 6508 return WifiMetricsProto.ROLE_CLIENT_SECONDARY_LONG_LIVED; 6509 } 6510 return WifiMetricsProto.ROLE_UNKNOWN; 6511 } 6512 clientRoleEnumToString(int role)6513 private static String clientRoleEnumToString(int role) { 6514 switch (role) { 6515 case WifiMetricsProto.ROLE_CLIENT_SCAN_ONLY: 6516 return "ROLE_CLIENT_SCAN_ONLY"; 6517 case WifiMetricsProto.ROLE_CLIENT_SECONDARY_TRANSIENT: 6518 return "ROLE_CLIENT_SECONDARY_TRANSIENT"; 6519 case WifiMetricsProto.ROLE_CLIENT_LOCAL_ONLY: 6520 return "ROLE_CLIENT_LOCAL_ONLY"; 6521 case WifiMetricsProto.ROLE_CLIENT_PRIMARY: 6522 return "ROLE_CLIENT_PRIMARY"; 6523 case WifiMetricsProto.ROLE_CLIENT_SECONDARY_LONG_LIVED: 6524 return "ROLE_CLIENT_SECONDARY_LONG_LIVED"; 6525 default: 6526 return "ROLE_UNKNOWN"; 6527 } 6528 } 6529 authFailureReasonToString(int authFailureReason)6530 private static String authFailureReasonToString(int authFailureReason) { 6531 switch (authFailureReason) { 6532 case StaEvent.AUTH_FAILURE_NONE: 6533 return "ERROR_AUTH_FAILURE_NONE"; 6534 case StaEvent.AUTH_FAILURE_TIMEOUT: 6535 return "ERROR_AUTH_FAILURE_TIMEOUT"; 6536 case StaEvent.AUTH_FAILURE_WRONG_PSWD: 6537 return "ERROR_AUTH_FAILURE_WRONG_PSWD"; 6538 case StaEvent.AUTH_FAILURE_EAP_FAILURE: 6539 return "ERROR_AUTH_FAILURE_EAP_FAILURE"; 6540 default: 6541 return ""; 6542 } 6543 } 6544 frameworkDisconnectReasonToString(int frameworkDisconnectReason)6545 private static String frameworkDisconnectReasonToString(int frameworkDisconnectReason) { 6546 switch (frameworkDisconnectReason) { 6547 case StaEvent.DISCONNECT_API: 6548 return "DISCONNECT_API"; 6549 case StaEvent.DISCONNECT_GENERIC: 6550 return "DISCONNECT_GENERIC"; 6551 case StaEvent.DISCONNECT_UNWANTED: 6552 return "DISCONNECT_UNWANTED"; 6553 case StaEvent.DISCONNECT_ROAM_WATCHDOG_TIMER: 6554 return "DISCONNECT_ROAM_WATCHDOG_TIMER"; 6555 case StaEvent.DISCONNECT_P2P_DISCONNECT_WIFI_REQUEST: 6556 return "DISCONNECT_P2P_DISCONNECT_WIFI_REQUEST"; 6557 case StaEvent.DISCONNECT_RESET_SIM_NETWORKS: 6558 return "DISCONNECT_RESET_SIM_NETWORKS"; 6559 case StaEvent.DISCONNECT_MBB_NO_INTERNET: 6560 return "DISCONNECT_MBB_NO_INTERNET"; 6561 case StaEvent.DISCONNECT_NETWORK_REMOVED: 6562 return "DISCONNECT_NETWORK_REMOVED"; 6563 case StaEvent.DISCONNECT_NETWORK_METERED: 6564 return "DISCONNECT_NETWORK_METERED"; 6565 case StaEvent.DISCONNECT_NETWORK_TEMPORARY_DISABLED: 6566 return "DISCONNECT_NETWORK_TEMPORARY_DISABLED"; 6567 case StaEvent.DISCONNECT_NETWORK_PERMANENT_DISABLED: 6568 return "DISCONNECT_NETWORK_PERMANENT_DISABLED"; 6569 case StaEvent.DISCONNECT_CARRIER_OFFLOAD_DISABLED: 6570 return "DISCONNECT_CARRIER_OFFLOAD_DISABLED"; 6571 case StaEvent.DISCONNECT_PASSPOINT_TAC: 6572 return "DISCONNECT_PASSPOINT_TAC"; 6573 case StaEvent.DISCONNECT_VCN_REQUEST: 6574 return "DISCONNECT_VCN_REQUEST"; 6575 case StaEvent.DISCONNECT_UNKNOWN_NETWORK: 6576 return "DISCONNECT_UNKNOWN_NETWORK"; 6577 default: 6578 return "DISCONNECT_UNKNOWN=" + frameworkDisconnectReason; 6579 } 6580 } 6581 configInfoToString(ConfigInfo info)6582 private static String configInfoToString(ConfigInfo info) { 6583 StringBuilder sb = new StringBuilder(); 6584 sb.append("ConfigInfo:") 6585 .append(" allowed_key_management=").append(info.allowedKeyManagement) 6586 .append(" allowed_protocols=").append(info.allowedProtocols) 6587 .append(" allowed_auth_algorithms=").append(info.allowedAuthAlgorithms) 6588 .append(" allowed_pairwise_ciphers=").append(info.allowedPairwiseCiphers) 6589 .append(" allowed_group_ciphers=").append(info.allowedGroupCiphers) 6590 .append(" hidden_ssid=").append(info.hiddenSsid) 6591 .append(" is_passpoint=").append(info.isPasspoint) 6592 .append(" is_ephemeral=").append(info.isEphemeral) 6593 .append(" has_ever_connected=").append(info.hasEverConnected) 6594 .append(" scan_rssi=").append(info.scanRssi) 6595 .append(" scan_freq=").append(info.scanFreq); 6596 return sb.toString(); 6597 } 6598 6599 /** 6600 * Converts the first 31 bits of a BitSet to a little endian int 6601 */ bitSetToInt(BitSet bits)6602 private static int bitSetToInt(BitSet bits) { 6603 int value = 0; 6604 int nBits = bits.length() < 31 ? bits.length() : 31; 6605 for (int i = 0; i < nBits; i++) { 6606 value += bits.get(i) ? (1 << i) : 0; 6607 } 6608 return value; 6609 } 6610 private void incrementSsid(SparseIntArray sia, int element) { 6611 increment(sia, Math.min(element, MAX_CONNECTABLE_SSID_NETWORK_BUCKET)); 6612 } 6613 private void incrementBssid(SparseIntArray sia, int element) { 6614 increment(sia, Math.min(element, MAX_CONNECTABLE_BSSID_NETWORK_BUCKET)); 6615 } 6616 private void incrementTotalScanResults(SparseIntArray sia, int element) { 6617 increment(sia, Math.min(element, MAX_TOTAL_SCAN_RESULTS_BUCKET)); 6618 } 6619 private void incrementTotalScanSsids(SparseIntArray sia, int element) { 6620 increment(sia, Math.min(element, MAX_TOTAL_SCAN_RESULT_SSIDS_BUCKET)); 6621 } 6622 private void incrementTotalPasspointAps(SparseIntArray sia, int element) { 6623 increment(sia, Math.min(element, MAX_TOTAL_PASSPOINT_APS_BUCKET)); 6624 } 6625 private void incrementTotalUniquePasspointEss(SparseIntArray sia, int element) { 6626 increment(sia, Math.min(element, MAX_TOTAL_PASSPOINT_UNIQUE_ESS_BUCKET)); 6627 } 6628 private void incrementPasspointPerUniqueEss(SparseIntArray sia, int element) { 6629 increment(sia, Math.min(element, MAX_PASSPOINT_APS_PER_UNIQUE_ESS_BUCKET)); 6630 } 6631 private void increment80211mcAps(SparseIntArray sia, int element) { 6632 increment(sia, Math.min(element, MAX_TOTAL_80211MC_APS_BUCKET)); 6633 } 6634 private void increment(SparseIntArray sia, int element) { 6635 int count = sia.get(element); 6636 sia.put(element, count + 1); 6637 } 6638 6639 private static class StaEventWithTime { 6640 public StaEvent staEvent; 6641 public long wallClockMillis; 6642 6643 StaEventWithTime(StaEvent event, long wallClockMillis) { 6644 staEvent = event; 6645 this.wallClockMillis = wallClockMillis; 6646 } 6647 6648 public String toString() { 6649 StringBuilder sb = new StringBuilder(); 6650 Calendar c = Calendar.getInstance(); 6651 c.setTimeInMillis(wallClockMillis); 6652 if (wallClockMillis != 0) { 6653 sb.append(String.format("%tm-%td %tH:%tM:%tS.%tL", c, c, c, c, c, c)); 6654 } else { 6655 sb.append(" "); 6656 } 6657 sb.append(" ").append(staEventToString(staEvent)); 6658 return sb.toString(); 6659 } 6660 } 6661 6662 private LinkedList<WifiIsUnusableWithTime> mWifiIsUnusableList = 6663 new LinkedList<WifiIsUnusableWithTime>(); 6664 private long mTxScucessDelta = 0; 6665 private long mTxRetriesDelta = 0; 6666 private long mTxBadDelta = 0; 6667 private long mRxSuccessDelta = 0; 6668 private long mLlStatsUpdateTimeDelta = 0; 6669 private long mLlStatsLastUpdateTime = 0; 6670 private int mLastScoreNoReset = -1; 6671 private long mLastDataStallTime = Long.MIN_VALUE; 6672 6673 private static class WifiIsUnusableWithTime { 6674 public WifiIsUnusableEvent event; 6675 public long wallClockMillis; 6676 6677 WifiIsUnusableWithTime(WifiIsUnusableEvent event, long wallClockMillis) { 6678 this.event = event; 6679 this.wallClockMillis = wallClockMillis; 6680 } 6681 6682 public String toString() { 6683 if (event == null) return "<NULL>"; 6684 StringBuilder sb = new StringBuilder(); 6685 if (wallClockMillis != 0) { 6686 Calendar c = Calendar.getInstance(); 6687 c.setTimeInMillis(wallClockMillis); 6688 sb.append(String.format("%tm-%td %tH:%tM:%tS.%tL", c, c, c, c, c, c)); 6689 } else { 6690 sb.append(" "); 6691 } 6692 sb.append(" "); 6693 6694 switch(event.type) { 6695 case WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX: 6696 sb.append("DATA_STALL_BAD_TX"); 6697 break; 6698 case WifiIsUnusableEvent.TYPE_DATA_STALL_TX_WITHOUT_RX: 6699 sb.append("DATA_STALL_TX_WITHOUT_RX"); 6700 break; 6701 case WifiIsUnusableEvent.TYPE_DATA_STALL_BOTH: 6702 sb.append("DATA_STALL_BOTH"); 6703 break; 6704 case WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT: 6705 sb.append("FIRMWARE_ALERT"); 6706 break; 6707 case WifiIsUnusableEvent.TYPE_IP_REACHABILITY_LOST: 6708 sb.append("IP_REACHABILITY_LOST"); 6709 break; 6710 default: 6711 sb.append("UNKNOWN " + event.type); 6712 break; 6713 } 6714 6715 sb.append(" lastScore=").append(event.lastScore); 6716 sb.append(" txSuccessDelta=").append(event.txSuccessDelta); 6717 sb.append(" txRetriesDelta=").append(event.txRetriesDelta); 6718 sb.append(" txBadDelta=").append(event.txBadDelta); 6719 sb.append(" rxSuccessDelta=").append(event.rxSuccessDelta); 6720 sb.append(" packetUpdateTimeDelta=").append(event.packetUpdateTimeDelta) 6721 .append("ms"); 6722 if (event.firmwareAlertCode != -1) { 6723 sb.append(" firmwareAlertCode=").append(event.firmwareAlertCode); 6724 } 6725 sb.append(" lastWifiUsabilityScore=").append(event.lastWifiUsabilityScore); 6726 sb.append(" lastPredictionHorizonSec=").append(event.lastPredictionHorizonSec); 6727 sb.append(" screenOn=").append(event.screenOn); 6728 sb.append(" mobileTxBytes=").append(event.mobileTxBytes); 6729 sb.append(" mobileRxBytes=").append(event.mobileRxBytes); 6730 sb.append(" totalTxBytes=").append(event.totalTxBytes); 6731 sb.append(" totalRxBytes=").append(event.totalRxBytes); 6732 return sb.toString(); 6733 } 6734 } 6735 6736 /** 6737 * Converts MeteredOverride enum to UserActionEvent type. 6738 * @param value 6739 */ 6740 public static int convertMeteredOverrideEnumToUserActionEventType(@MeteredOverride int value) { 6741 int result = UserActionEvent.EVENT_UNKNOWN; 6742 switch(value) { 6743 case WifiConfiguration.METERED_OVERRIDE_NONE: 6744 result = UserActionEvent.EVENT_CONFIGURE_METERED_STATUS_AUTO; 6745 break; 6746 case WifiConfiguration.METERED_OVERRIDE_METERED: 6747 result = UserActionEvent.EVENT_CONFIGURE_METERED_STATUS_METERED; 6748 break; 6749 case WifiConfiguration.METERED_OVERRIDE_NOT_METERED: 6750 result = UserActionEvent.EVENT_CONFIGURE_METERED_STATUS_UNMETERED; 6751 break; 6752 } 6753 return result; 6754 } 6755 6756 /** 6757 * Converts Adaptive Connectivity state to UserActionEvent type. 6758 * @param value 6759 */ 6760 public static int convertAdaptiveConnectivityStateToUserActionEventType(boolean value) { 6761 return value ? UserActionEvent.EVENT_CONFIGURE_ADAPTIVE_CONNECTIVITY_ON 6762 : UserActionEvent.EVENT_CONFIGURE_ADAPTIVE_CONNECTIVITY_OFF; 6763 } 6764 6765 static class MeteredNetworkStatsBuilder { 6766 // A map from network identifier to MeteredDetail 6767 Map<String, MeteredDetail> mNetworkMap = new ArrayMap<>(); 6768 6769 void put(WifiConfiguration config, boolean detectedAsMetered) { 6770 MeteredDetail meteredDetail = new MeteredDetail(); 6771 boolean isMetered = detectedAsMetered; 6772 if (config.meteredOverride == WifiConfiguration.METERED_OVERRIDE_METERED) { 6773 isMetered = true; 6774 } else if (config.meteredOverride == WifiConfiguration.METERED_OVERRIDE_NOT_METERED) { 6775 isMetered = false; 6776 } 6777 meteredDetail.isMetered = isMetered; 6778 meteredDetail.isMeteredOverrideSet = config.meteredOverride 6779 != WifiConfiguration.METERED_OVERRIDE_NONE; 6780 meteredDetail.isFromSuggestion = config.fromWifiNetworkSuggestion; 6781 mNetworkMap.put(config.getProfileKey(), meteredDetail); 6782 } 6783 6784 void clear() { 6785 mNetworkMap.clear(); 6786 } 6787 6788 MeteredNetworkStats toProto(boolean isFromSuggestion) { 6789 MeteredNetworkStats result = new MeteredNetworkStats(); 6790 for (MeteredDetail meteredDetail : mNetworkMap.values()) { 6791 if (meteredDetail.isFromSuggestion != isFromSuggestion) { 6792 continue; 6793 } 6794 if (meteredDetail.isMetered) { 6795 result.numMetered++; 6796 } else { 6797 result.numUnmetered++; 6798 } 6799 if (meteredDetail.isMeteredOverrideSet) { 6800 if (meteredDetail.isMetered) { 6801 result.numOverrideMetered++; 6802 } else { 6803 result.numOverrideUnmetered++; 6804 } 6805 } 6806 } 6807 return result; 6808 } 6809 6810 static class MeteredDetail { 6811 public boolean isMetered; 6812 public boolean isMeteredOverrideSet; 6813 public boolean isFromSuggestion; 6814 } 6815 } 6816 6817 /** 6818 * Add metered information of this network. 6819 * @param config WifiConfiguration representing the netework. 6820 * @param detectedAsMetered is the network detected as metered. 6821 */ 6822 public void addMeteredStat(WifiConfiguration config, boolean detectedAsMetered) { 6823 synchronized (mLock) { 6824 if (config == null) { 6825 return; 6826 } 6827 mMeteredNetworkStatsBuilder.put(config, detectedAsMetered); 6828 } 6829 } 6830 /** 6831 * Logs a UserActionEvent without a target network. 6832 * @param eventType the type of user action (one of WifiMetricsProto.UserActionEvent.EventType) 6833 */ 6834 public void logUserActionEvent(int eventType) { 6835 logUserActionEvent(eventType, -1); 6836 } 6837 6838 /** 6839 * Logs a UserActionEvent which has a target network. 6840 * @param eventType the type of user action (one of WifiMetricsProto.UserActionEvent.EventType) 6841 * @param networkId networkId of the target network. 6842 */ 6843 public void logUserActionEvent(int eventType, int networkId) { 6844 synchronized (mLock) { 6845 mUserActionEventList.add(new UserActionEventWithTime(eventType, networkId)); 6846 if (mUserActionEventList.size() > MAX_USER_ACTION_EVENTS) { 6847 mUserActionEventList.remove(); 6848 } 6849 } 6850 } 6851 6852 /** 6853 * Logs a UserActionEvent, directly specifying the target network's properties. 6854 * @param eventType the type of user action (one of WifiMetricsProto.UserActionEvent.EventType) 6855 * @param isEphemeral true if the target network is ephemeral. 6856 * @param isPasspoint true if the target network is passpoint. 6857 */ 6858 public void logUserActionEvent(int eventType, boolean isEphemeral, boolean isPasspoint) { 6859 synchronized (mLock) { 6860 TargetNetworkInfo networkInfo = new TargetNetworkInfo(); 6861 networkInfo.isEphemeral = isEphemeral; 6862 networkInfo.isPasspoint = isPasspoint; 6863 mUserActionEventList.add(new UserActionEventWithTime(eventType, networkInfo)); 6864 if (mUserActionEventList.size() > MAX_USER_ACTION_EVENTS) { 6865 mUserActionEventList.remove(); 6866 } 6867 } 6868 } 6869 6870 /** 6871 * Update the difference between the last two WifiLinkLayerStats for WifiIsUnusableEvent 6872 */ 6873 public void updateWifiIsUnusableLinkLayerStats(long txSuccessDelta, long txRetriesDelta, 6874 long txBadDelta, long rxSuccessDelta, long updateTimeDelta) { 6875 mTxScucessDelta = txSuccessDelta; 6876 mTxRetriesDelta = txRetriesDelta; 6877 mTxBadDelta = txBadDelta; 6878 mRxSuccessDelta = rxSuccessDelta; 6879 mLlStatsUpdateTimeDelta = updateTimeDelta; 6880 mLlStatsLastUpdateTime = mClock.getElapsedSinceBootMillis(); 6881 } 6882 6883 /** 6884 * Clear the saved difference between the last two WifiLinkLayerStats 6885 */ 6886 public void resetWifiIsUnusableLinkLayerStats() { 6887 mTxScucessDelta = 0; 6888 mTxRetriesDelta = 0; 6889 mTxBadDelta = 0; 6890 mRxSuccessDelta = 0; 6891 mLlStatsUpdateTimeDelta = 0; 6892 mLlStatsLastUpdateTime = 0; 6893 mLastDataStallTime = Long.MIN_VALUE; 6894 } 6895 6896 /** 6897 * Log a WifiIsUnusableEvent 6898 * @param triggerType WifiIsUnusableEvent.type describing the event 6899 * @param ifaceName name of the interface. 6900 */ 6901 public void logWifiIsUnusableEvent(String ifaceName, int triggerType) { 6902 logWifiIsUnusableEvent(ifaceName, triggerType, -1); 6903 } 6904 6905 /** 6906 * Log a WifiIsUnusableEvent 6907 * @param triggerType WifiIsUnusableEvent.type describing the event 6908 * @param firmwareAlertCode WifiIsUnusableEvent.firmwareAlertCode for firmware alert code 6909 * @param ifaceName name of the interface. 6910 */ 6911 public void logWifiIsUnusableEvent(String ifaceName, int triggerType, int firmwareAlertCode) { 6912 if (!isPrimary(ifaceName)) { 6913 return; 6914 } 6915 mScoreBreachLowTimeMillis = -1; 6916 6917 long currentBootTime = mClock.getElapsedSinceBootMillis(); 6918 switch (triggerType) { 6919 case WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX: 6920 case WifiIsUnusableEvent.TYPE_DATA_STALL_TX_WITHOUT_RX: 6921 case WifiIsUnusableEvent.TYPE_DATA_STALL_BOTH: 6922 // Have a time-based throttle for generating WifiIsUnusableEvent from data stalls 6923 if (currentBootTime < mLastDataStallTime + MIN_DATA_STALL_WAIT_MS) { 6924 return; 6925 } 6926 mLastDataStallTime = currentBootTime; 6927 break; 6928 case WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT: 6929 break; 6930 case WifiIsUnusableEvent.TYPE_IP_REACHABILITY_LOST: 6931 break; 6932 default: 6933 Log.e(TAG, "Unknown WifiIsUnusableEvent: " + triggerType); 6934 return; 6935 } 6936 6937 WifiIsUnusableEvent event = new WifiIsUnusableEvent(); 6938 event.type = triggerType; 6939 if (triggerType == WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT) { 6940 event.firmwareAlertCode = firmwareAlertCode; 6941 } 6942 event.startTimeMillis = currentBootTime; 6943 event.lastScore = mLastScoreNoReset; 6944 event.lastWifiUsabilityScore = mLastWifiUsabilityScoreNoReset; 6945 event.lastPredictionHorizonSec = mLastPredictionHorizonSecNoReset; 6946 event.txSuccessDelta = mTxScucessDelta; 6947 event.txRetriesDelta = mTxRetriesDelta; 6948 event.txBadDelta = mTxBadDelta; 6949 event.rxSuccessDelta = mRxSuccessDelta; 6950 event.packetUpdateTimeDelta = mLlStatsUpdateTimeDelta; 6951 event.lastLinkLayerStatsUpdateTime = mLlStatsLastUpdateTime; 6952 event.screenOn = mScreenOn; 6953 event.mobileTxBytes = mFacade.getMobileTxBytes(); 6954 event.mobileRxBytes = mFacade.getMobileRxBytes(); 6955 event.totalTxBytes = mFacade.getTotalTxBytes(); 6956 event.totalRxBytes = mFacade.getTotalRxBytes(); 6957 6958 mWifiIsUnusableList.add(new WifiIsUnusableWithTime(event, mClock.getWallClockMillis())); 6959 if (mWifiIsUnusableList.size() > MAX_UNUSABLE_EVENTS) { 6960 mWifiIsUnusableList.removeFirst(); 6961 } 6962 WifiUsabilityState wifiUsabilityState = mWifiUsabilityStatePerIface.getOrDefault( 6963 ifaceName, WifiUsabilityState.UNKNOWN); 6964 6965 WifiStatsLog.write(WIFI_IS_UNUSABLE_REPORTED, 6966 convertWifiUnUsableTypeToProto(triggerType), 6967 mScorerUid, wifiUsabilityState == WifiUsabilityState.USABLE, 6968 convertWifiUsabilityState(wifiUsabilityState)); 6969 } 6970 6971 private int convertWifiUsabilityState(WifiUsabilityState usabilityState) { 6972 if (usabilityState == WifiUsabilityState.USABLE) { 6973 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__WIFI_PREDICTED_USABILITY_STATE__WIFI_USABILITY_PREDICTED_USABLE; 6974 } else if (usabilityState == WifiUsabilityState.UNUSABLE) { 6975 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__WIFI_PREDICTED_USABILITY_STATE__WIFI_USABILITY_PREDICTED_UNUSABLE; 6976 } else { 6977 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__WIFI_PREDICTED_USABILITY_STATE__WIFI_USABILITY_PREDICTED_UNKNOWN; 6978 } 6979 } 6980 6981 private int convertWifiUnUsableTypeToProto(int triggerType) { 6982 switch (triggerType) { 6983 case WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX: 6984 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__TYPE__TYPE_DATA_STALL_BAD_TX; 6985 case WifiIsUnusableEvent.TYPE_DATA_STALL_TX_WITHOUT_RX: 6986 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__TYPE__TYPE_DATA_STALL_TX_WITHOUT_RX; 6987 case WifiIsUnusableEvent.TYPE_DATA_STALL_BOTH: 6988 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__TYPE__TYPE_DATA_STALL_BOTH; 6989 case WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT: 6990 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__TYPE__TYPE_FIRMWARE_ALERT; 6991 case WifiIsUnusableEvent.TYPE_IP_REACHABILITY_LOST: 6992 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__TYPE__TYPE_IP_REACHABILITY_LOST; 6993 default: 6994 return WifiStatsLog.WIFI_IS_UNUSABLE_REPORTED__TYPE__TYPE_UNKNOWN; 6995 } 6996 } 6997 6998 /** 6999 * Extract data from |info| and |stats| to build a WifiUsabilityStatsEntry and then adds it 7000 * into an internal ring buffer. 7001 * @param info 7002 * @param stats 7003 * @param ifaceName 7004 */ 7005 public void updateWifiUsabilityStatsEntries(String ifaceName, WifiInfo info, 7006 WifiLinkLayerStats stats) { 7007 // This is only collected for primary STA currently because RSSI polling is disabled for 7008 // non-primary STAs. 7009 synchronized (mLock) { 7010 if (info == null) { 7011 return; 7012 } 7013 if (stats == null) { 7014 // For devices lacking vendor hal, fill in the parts that we can 7015 stats = new WifiLinkLayerStats(); 7016 stats.timeStampInMs = mClock.getElapsedSinceBootMillis(); 7017 stats.txmpdu_be = info.txSuccess; 7018 stats.retries_be = info.txRetries; 7019 stats.lostmpdu_be = info.txBad; 7020 stats.rxmpdu_be = info.rxSuccess; 7021 } 7022 WifiUsabilityStatsEntry wifiUsabilityStatsEntry = 7023 mWifiUsabilityStatsEntriesList.size() 7024 < MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE 7025 ? new WifiUsabilityStatsEntry() : mWifiUsabilityStatsEntriesList.remove(); 7026 wifiUsabilityStatsEntry.timeStampMs = stats.timeStampInMs; 7027 wifiUsabilityStatsEntry.totalTxSuccess = stats.txmpdu_be + stats.txmpdu_bk 7028 + stats.txmpdu_vi + stats.txmpdu_vo; 7029 wifiUsabilityStatsEntry.totalTxRetries = stats.retries_be + stats.retries_bk 7030 + stats.retries_vi + stats.retries_vo; 7031 wifiUsabilityStatsEntry.totalTxBad = stats.lostmpdu_be + stats.lostmpdu_bk 7032 + stats.lostmpdu_vi + stats.lostmpdu_vo; 7033 wifiUsabilityStatsEntry.totalRxSuccess = stats.rxmpdu_be + stats.rxmpdu_bk 7034 + stats.rxmpdu_vi + stats.rxmpdu_vo; 7035 /* Update per radio stats */ 7036 if (stats.radioStats != null && stats.radioStats.length > 0) { 7037 int numRadios = stats.radioStats.length; 7038 wifiUsabilityStatsEntry.radioStats = 7039 new RadioStats[numRadios]; 7040 for (int i = 0; i < numRadios; i++) { 7041 RadioStats radioStats = new RadioStats(); 7042 WifiLinkLayerStats.RadioStat radio = stats.radioStats[i]; 7043 radioStats.radioId = radio.radio_id; 7044 radioStats.totalRadioOnTimeMs = radio.on_time; 7045 radioStats.totalRadioTxTimeMs = radio.tx_time; 7046 radioStats.totalRadioRxTimeMs = radio.rx_time; 7047 radioStats.totalScanTimeMs = radio.on_time_scan; 7048 radioStats.totalNanScanTimeMs = radio.on_time_nan_scan; 7049 radioStats.totalBackgroundScanTimeMs = radio.on_time_background_scan; 7050 radioStats.totalRoamScanTimeMs = radio.on_time_roam_scan; 7051 radioStats.totalPnoScanTimeMs = radio.on_time_pno_scan; 7052 radioStats.totalHotspot2ScanTimeMs = radio.on_time_hs20_scan; 7053 wifiUsabilityStatsEntry.radioStats[i] = radioStats; 7054 } 7055 } 7056 wifiUsabilityStatsEntry.totalRadioOnTimeMs = stats.on_time; 7057 wifiUsabilityStatsEntry.totalRadioTxTimeMs = stats.tx_time; 7058 wifiUsabilityStatsEntry.totalRadioRxTimeMs = stats.rx_time; 7059 wifiUsabilityStatsEntry.totalScanTimeMs = stats.on_time_scan; 7060 wifiUsabilityStatsEntry.totalNanScanTimeMs = stats.on_time_nan_scan; 7061 wifiUsabilityStatsEntry.totalBackgroundScanTimeMs = stats.on_time_background_scan; 7062 wifiUsabilityStatsEntry.totalRoamScanTimeMs = stats.on_time_roam_scan; 7063 wifiUsabilityStatsEntry.totalPnoScanTimeMs = stats.on_time_pno_scan; 7064 wifiUsabilityStatsEntry.totalHotspot2ScanTimeMs = stats.on_time_hs20_scan; 7065 wifiUsabilityStatsEntry.rssi = info.getRssi(); 7066 wifiUsabilityStatsEntry.linkSpeedMbps = info.getLinkSpeed(); 7067 WifiLinkLayerStats.ChannelStats statsMap = 7068 stats.channelStatsMap.get(info.getFrequency()); 7069 if (statsMap != null) { 7070 wifiUsabilityStatsEntry.totalRadioOnFreqTimeMs = statsMap.radioOnTimeMs; 7071 wifiUsabilityStatsEntry.totalCcaBusyFreqTimeMs = statsMap.ccaBusyTimeMs; 7072 } 7073 wifiUsabilityStatsEntry.totalBeaconRx = stats.beacon_rx; 7074 mLastTotalBeaconRx = stats.beacon_rx; 7075 wifiUsabilityStatsEntry.timeSliceDutyCycleInPercent = stats.timeSliceDutyCycleInPercent; 7076 7077 boolean isSameBssidAndFreq = mLastBssid == null || mLastFrequency == -1 7078 || (mLastBssid.equals(info.getBSSID()) 7079 && mLastFrequency == info.getFrequency()); 7080 mLastBssid = info.getBSSID(); 7081 mLastFrequency = info.getFrequency(); 7082 wifiUsabilityStatsEntry.wifiScore = mLastScoreNoReset; 7083 wifiUsabilityStatsEntry.wifiUsabilityScore = mLastWifiUsabilityScoreNoReset; 7084 wifiUsabilityStatsEntry.seqNumToFramework = mSeqNumToFramework; 7085 wifiUsabilityStatsEntry.predictionHorizonSec = mLastPredictionHorizonSecNoReset; 7086 switch (mProbeStatusSinceLastUpdate) { 7087 case android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE: 7088 wifiUsabilityStatsEntry.probeStatusSinceLastUpdate = 7089 WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE; 7090 break; 7091 case android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_SUCCESS: 7092 wifiUsabilityStatsEntry.probeStatusSinceLastUpdate = 7093 WifiUsabilityStatsEntry.PROBE_STATUS_SUCCESS; 7094 break; 7095 case android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_FAILURE: 7096 wifiUsabilityStatsEntry.probeStatusSinceLastUpdate = 7097 WifiUsabilityStatsEntry.PROBE_STATUS_FAILURE; 7098 break; 7099 default: 7100 wifiUsabilityStatsEntry.probeStatusSinceLastUpdate = 7101 WifiUsabilityStatsEntry.PROBE_STATUS_UNKNOWN; 7102 Log.e(TAG, "Unknown link probe status: " + mProbeStatusSinceLastUpdate); 7103 } 7104 wifiUsabilityStatsEntry.probeElapsedTimeSinceLastUpdateMs = 7105 mProbeElapsedTimeSinceLastUpdateMs; 7106 wifiUsabilityStatsEntry.probeMcsRateSinceLastUpdate = mProbeMcsRateSinceLastUpdate; 7107 wifiUsabilityStatsEntry.rxLinkSpeedMbps = info.getRxLinkSpeedMbps(); 7108 wifiUsabilityStatsEntry.isSameBssidAndFreq = isSameBssidAndFreq; 7109 wifiUsabilityStatsEntry.seqNumInsideFramework = mSeqNumInsideFramework; 7110 wifiUsabilityStatsEntry.deviceMobilityState = mCurrentDeviceMobilityState; 7111 wifiUsabilityStatsEntry.contentionTimeStats = 7112 new ContentionTimeStats[NUM_WME_ACCESS_CATEGORIES]; 7113 for (int ac = 0; ac < NUM_WME_ACCESS_CATEGORIES; ac++) { 7114 ContentionTimeStats contentionTimeStats = new ContentionTimeStats(); 7115 switch (ac) { 7116 case ContentionTimeStats.WME_ACCESS_CATEGORY_BE: 7117 contentionTimeStats.accessCategory = 7118 ContentionTimeStats.WME_ACCESS_CATEGORY_BE; 7119 contentionTimeStats.contentionTimeMinMicros = 7120 stats.contentionTimeMinBeInUsec; 7121 contentionTimeStats.contentionTimeMaxMicros = 7122 stats.contentionTimeMaxBeInUsec; 7123 contentionTimeStats.contentionTimeAvgMicros = 7124 stats.contentionTimeAvgBeInUsec; 7125 contentionTimeStats.contentionNumSamples = 7126 stats.contentionNumSamplesBe; 7127 break; 7128 case ContentionTimeStats.WME_ACCESS_CATEGORY_BK: 7129 contentionTimeStats.accessCategory = 7130 ContentionTimeStats.WME_ACCESS_CATEGORY_BK; 7131 contentionTimeStats.contentionTimeMinMicros = 7132 stats.contentionTimeMinBkInUsec; 7133 contentionTimeStats.contentionTimeMaxMicros = 7134 stats.contentionTimeMaxBkInUsec; 7135 contentionTimeStats.contentionTimeAvgMicros = 7136 stats.contentionTimeAvgBkInUsec; 7137 contentionTimeStats.contentionNumSamples = 7138 stats.contentionNumSamplesBk; 7139 break; 7140 case ContentionTimeStats.WME_ACCESS_CATEGORY_VI: 7141 contentionTimeStats.accessCategory = 7142 ContentionTimeStats.WME_ACCESS_CATEGORY_VI; 7143 contentionTimeStats.contentionTimeMinMicros = 7144 stats.contentionTimeMinViInUsec; 7145 contentionTimeStats.contentionTimeMaxMicros = 7146 stats.contentionTimeMaxViInUsec; 7147 contentionTimeStats.contentionTimeAvgMicros = 7148 stats.contentionTimeAvgViInUsec; 7149 contentionTimeStats.contentionNumSamples = 7150 stats.contentionNumSamplesVi; 7151 break; 7152 case ContentionTimeStats.WME_ACCESS_CATEGORY_VO: 7153 contentionTimeStats.accessCategory = 7154 ContentionTimeStats.WME_ACCESS_CATEGORY_VO; 7155 contentionTimeStats.contentionTimeMinMicros = 7156 stats.contentionTimeMinVoInUsec; 7157 contentionTimeStats.contentionTimeMaxMicros = 7158 stats.contentionTimeMaxVoInUsec; 7159 contentionTimeStats.contentionTimeAvgMicros = 7160 stats.contentionTimeAvgVoInUsec; 7161 contentionTimeStats.contentionNumSamples = 7162 stats.contentionNumSamplesVo; 7163 break; 7164 default: 7165 Log.e(TAG, "Unknown WME Access Category: " + ac); 7166 } 7167 wifiUsabilityStatsEntry.contentionTimeStats[ac] = contentionTimeStats; 7168 } 7169 if (mWifiChannelUtilization != null) { 7170 wifiUsabilityStatsEntry.channelUtilizationRatio = 7171 mWifiChannelUtilization.getUtilizationRatio(mLastFrequency); 7172 } 7173 if (mWifiDataStall != null) { 7174 wifiUsabilityStatsEntry.isThroughputSufficient = 7175 mWifiDataStall.isThroughputSufficient(); 7176 wifiUsabilityStatsEntry.isCellularDataAvailable = 7177 mWifiDataStall.isCellularDataAvailable(); 7178 } 7179 if (mWifiSettingsStore != null) { 7180 wifiUsabilityStatsEntry.isWifiScoringEnabled = 7181 mWifiSettingsStore.isWifiScoringEnabled(); 7182 } 7183 // Here it is assumed there is only one peer information from HAL and the peer is the 7184 // AP that STA is associated with. 7185 if (stats.peerInfo != null && stats.peerInfo.length > 0 7186 && stats.peerInfo[0].rateStats != null) { 7187 wifiUsabilityStatsEntry.staCount = stats.peerInfo[0].staCount; 7188 wifiUsabilityStatsEntry.channelUtilization = stats.peerInfo[0].chanUtil; 7189 int numRates = stats.peerInfo[0].rateStats != null 7190 ? stats.peerInfo[0].rateStats.length : 0; 7191 wifiUsabilityStatsEntry.rateStats = new RateStats[numRates]; 7192 for (int i = 0; i < numRates; i++) { 7193 RateStats rate = new RateStats(); 7194 WifiLinkLayerStats.RateStat curRate = stats.peerInfo[0].rateStats[i]; 7195 rate.preamble = curRate.preamble; 7196 rate.nss = curRate.nss; 7197 rate.bw = curRate.bw; 7198 rate.rateMcsIdx = curRate.rateMcsIdx; 7199 rate.bitRateInKbps = curRate.bitRateInKbps; 7200 rate.txMpdu = curRate.txMpdu; 7201 rate.rxMpdu = curRate.rxMpdu; 7202 rate.mpduLost = curRate.mpduLost; 7203 rate.retries = curRate.retries; 7204 wifiUsabilityStatsEntry.rateStats[i] = rate; 7205 } 7206 } 7207 7208 mWifiUsabilityStatsEntriesList.add(wifiUsabilityStatsEntry); 7209 mWifiUsabilityStatsCounter++; 7210 if (mWifiUsabilityStatsCounter >= NUM_WIFI_USABILITY_STATS_ENTRIES_PER_WIFI_GOOD) { 7211 addToWifiUsabilityStatsList(ifaceName, WifiUsabilityStats.LABEL_GOOD, 7212 WifiUsabilityStats.TYPE_UNKNOWN, -1); 7213 } 7214 if (mScoreBreachLowTimeMillis != -1) { 7215 long elapsedTime = mClock.getElapsedSinceBootMillis() - mScoreBreachLowTimeMillis; 7216 if (elapsedTime >= MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS) { 7217 mScoreBreachLowTimeMillis = -1; 7218 if (elapsedTime <= VALIDITY_PERIOD_OF_SCORE_BREACH_LOW_MS) { 7219 addToWifiUsabilityStatsList(ifaceName, WifiUsabilityStats.LABEL_GOOD, 7220 WifiUsabilityStats.TYPE_UNKNOWN, -1); 7221 } 7222 } 7223 } 7224 7225 // Invoke Wifi usability stats listener. 7226 // TODO(b/179518316): Enable this for secondary transient STA also if external scorer 7227 // is in charge of MBB. 7228 if (isPrimary(ifaceName)) { 7229 sendWifiUsabilityStats(mSeqNumInsideFramework, isSameBssidAndFreq, 7230 createNewWifiUsabilityStatsEntryParcelable(wifiUsabilityStatsEntry, stats, 7231 info)); 7232 } 7233 7234 mSeqNumInsideFramework++; 7235 mProbeStatusSinceLastUpdate = 7236 android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE; 7237 mProbeElapsedTimeSinceLastUpdateMs = -1; 7238 mProbeMcsRateSinceLastUpdate = -1; 7239 } 7240 } 7241 7242 /** 7243 * Send Wifi usability stats. 7244 * @param seqNum 7245 * @param isSameBssidAndFreq 7246 * @param statsEntry 7247 */ 7248 private void sendWifiUsabilityStats(int seqNum, boolean isSameBssidAndFreq, 7249 android.net.wifi.WifiUsabilityStatsEntry statsEntry) { 7250 int itemCount = mOnWifiUsabilityListeners.beginBroadcast(); 7251 for (int i = 0; i < itemCount; i++) { 7252 try { 7253 mOnWifiUsabilityListeners.getBroadcastItem(i).onWifiUsabilityStats(seqNum, 7254 isSameBssidAndFreq, statsEntry); 7255 } catch (RemoteException e) { 7256 Log.e(TAG, "Unable to invoke Wifi usability stats entry listener ", e); 7257 } 7258 } 7259 mOnWifiUsabilityListeners.finishBroadcast(); 7260 } 7261 7262 private android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats[] 7263 convertContentionTimeStats(WifiLinkLayerStats.LinkSpecificStats stats) { 7264 android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats[] contentionTimeStatsArray = 7265 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats[ 7266 android.net.wifi.WifiUsabilityStatsEntry.NUM_WME_ACCESS_CATEGORIES]; 7267 for (int ac = 0; ac < android.net.wifi.WifiUsabilityStatsEntry.NUM_WME_ACCESS_CATEGORIES; 7268 ac++) { 7269 android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats contentionTimeStats = null; 7270 switch (ac) { 7271 case android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_BE: 7272 contentionTimeStats = 7273 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats( 7274 stats.contentionTimeMinBeInUsec, 7275 stats.contentionTimeMaxBeInUsec, 7276 stats.contentionTimeAvgBeInUsec, 7277 stats.contentionNumSamplesBe 7278 ); 7279 break; 7280 case android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_BK: 7281 contentionTimeStats = 7282 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats( 7283 stats.contentionTimeMinBkInUsec, 7284 stats.contentionTimeMaxBkInUsec, 7285 stats.contentionTimeAvgBkInUsec, 7286 stats.contentionNumSamplesBk 7287 ); 7288 break; 7289 case android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_VO: 7290 contentionTimeStats = 7291 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats( 7292 stats.contentionTimeMinVoInUsec, 7293 stats.contentionTimeMaxVoInUsec, 7294 stats.contentionTimeAvgVoInUsec, 7295 stats.contentionNumSamplesVo 7296 ); 7297 break; 7298 case android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_VI: 7299 contentionTimeStats = 7300 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats( 7301 stats.contentionTimeMinViInUsec, 7302 stats.contentionTimeMaxViInUsec, 7303 stats.contentionTimeAvgViInUsec, 7304 stats.contentionNumSamplesVi 7305 ); 7306 break; 7307 default: 7308 Log.d(TAG, "Unknown WME Access Category: " + ac); 7309 contentionTimeStats = null; 7310 } 7311 contentionTimeStatsArray[ac] = contentionTimeStats; 7312 } 7313 return contentionTimeStatsArray; 7314 } 7315 7316 private android.net.wifi.WifiUsabilityStatsEntry.RateStats[] convertRateStats( 7317 WifiLinkLayerStats.LinkSpecificStats stats) { 7318 android.net.wifi.WifiUsabilityStatsEntry.RateStats[] rateStats = null; 7319 if (stats.peerInfo != null && stats.peerInfo.length > 0 7320 && stats.peerInfo[0].rateStats != null) { 7321 int numRates = stats.peerInfo[0].rateStats != null 7322 ? stats.peerInfo[0].rateStats.length : 0; 7323 rateStats = new android.net.wifi.WifiUsabilityStatsEntry.RateStats[numRates]; 7324 for (int i = 0; i < numRates; i++) { 7325 WifiLinkLayerStats.RateStat curRate = stats.peerInfo[0].rateStats[i]; 7326 android.net.wifi.WifiUsabilityStatsEntry.RateStats rate = 7327 new android.net.wifi.WifiUsabilityStatsEntry.RateStats( 7328 convertPreambleTypeEnumToUsabilityStatsType(curRate.preamble), 7329 convertSpatialStreamEnumToUsabilityStatsType(curRate.nss), 7330 convertBandwidthEnumToUsabilityStatsType(curRate.bw), 7331 curRate.rateMcsIdx, curRate.bitRateInKbps, 7332 curRate.txMpdu, curRate.rxMpdu, curRate.mpduLost, curRate.retries); 7333 rateStats[i] = rate; 7334 } 7335 } 7336 return rateStats; 7337 } 7338 7339 private SparseArray<android.net.wifi.WifiUsabilityStatsEntry.LinkStats> convertLinkStats( 7340 WifiLinkLayerStats stats, WifiInfo info) { 7341 SparseArray<android.net.wifi.WifiUsabilityStatsEntry.LinkStats> linkStats = 7342 new SparseArray<>(); 7343 if (stats == null || stats.links == null || stats.links.length == 0) return linkStats; 7344 // Create a link id to MLO link mapping 7345 SparseArray<MloLink> mloLinks = new SparseArray<>(); 7346 for (MloLink link: info.getAffiliatedMloLinks()) { 7347 mloLinks.put(link.getLinkId(), link); 7348 } 7349 mLastLinkMetrics.clear(); 7350 // Fill per link stats. 7351 for (WifiLinkLayerStats.LinkSpecificStats inStat : stats.links) { 7352 if (inStat == null) break; 7353 LinkMetrics linkMetrics = new LinkMetrics(); 7354 linkMetrics.setTotalBeaconRx(inStat.beacon_rx); 7355 linkMetrics.setLinkUsageState(inStat.state); 7356 mLastLinkMetrics.put(inStat.link_id, linkMetrics); 7357 WifiLinkLayerStats.ChannelStats channelStatsMap = stats.channelStatsMap.get( 7358 inStat.frequencyMhz); 7359 // Note: RSSI, Tx & Rx link speed are derived from signal poll stats which is updated in 7360 // Mlolink or WifiInfo (non-MLO case). 7361 android.net.wifi.WifiUsabilityStatsEntry.LinkStats outStat = 7362 new android.net.wifi.WifiUsabilityStatsEntry.LinkStats(inStat.link_id, 7363 inStat.state, inStat.radio_id, 7364 (mloLinks.size() > 0) ? mloLinks.get(inStat.link_id, 7365 new MloLink()).getRssi() : info.getRssi(), 7366 (mloLinks.size() > 0) ? mloLinks.get(inStat.link_id, 7367 new MloLink()).getTxLinkSpeedMbps() : info.getTxLinkSpeedMbps(), 7368 (mloLinks.size() > 0) ? mloLinks.get(inStat.link_id, 7369 new MloLink()).getRxLinkSpeedMbps() : info.getRxLinkSpeedMbps(), 7370 inStat.txmpdu_be + inStat.txmpdu_bk + inStat.txmpdu_vi 7371 + inStat.txmpdu_vo, 7372 inStat.retries_be + inStat.retries_bk + inStat.retries_vi 7373 + inStat.retries_vo, 7374 inStat.lostmpdu_be + inStat.lostmpdu_bk + inStat.lostmpdu_vo 7375 + inStat.lostmpdu_vi, 7376 inStat.rxmpdu_be + inStat.rxmpdu_bk + inStat.rxmpdu_vo 7377 + inStat.rxmpdu_vi, 7378 inStat.beacon_rx, inStat.timeSliceDutyCycleInPercent, 7379 (channelStatsMap != null) ? channelStatsMap.ccaBusyTimeMs : 0 , 7380 (channelStatsMap != null) ? channelStatsMap.radioOnTimeMs : 0, 7381 convertContentionTimeStats(inStat), 7382 convertRateStats(inStat)); 7383 linkStats.put(inStat.link_id, outStat); 7384 } 7385 7386 return linkStats; 7387 } 7388 7389 private android.net.wifi.WifiUsabilityStatsEntry createNewWifiUsabilityStatsEntryParcelable( 7390 WifiUsabilityStatsEntry s, WifiLinkLayerStats stats, WifiInfo info) { 7391 int probeStatus; 7392 switch (s.probeStatusSinceLastUpdate) { 7393 case WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE: 7394 probeStatus = android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE; 7395 break; 7396 case WifiUsabilityStatsEntry.PROBE_STATUS_SUCCESS: 7397 probeStatus = android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_SUCCESS; 7398 break; 7399 case WifiUsabilityStatsEntry.PROBE_STATUS_FAILURE: 7400 probeStatus = android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_FAILURE; 7401 break; 7402 default: 7403 probeStatus = android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_UNKNOWN; 7404 Log.e(TAG, "Unknown link probe status: " + s.probeStatusSinceLastUpdate); 7405 } 7406 android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats[] contentionTimeStats = 7407 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats[ 7408 android.net.wifi.WifiUsabilityStatsEntry.NUM_WME_ACCESS_CATEGORIES]; 7409 createNewContentionTimeStatsParcelable(contentionTimeStats, s.contentionTimeStats); 7410 int numRates = s.rateStats != null ? s.rateStats.length : 0; 7411 android.net.wifi.WifiUsabilityStatsEntry.RateStats[] rateStats = 7412 new android.net.wifi.WifiUsabilityStatsEntry.RateStats[numRates]; 7413 createNewRateStatsParcelable(rateStats, s.rateStats); 7414 int numRadios = s.radioStats != null ? s.radioStats.length : 0; 7415 android.net.wifi.WifiUsabilityStatsEntry.RadioStats[] radioStats = 7416 new android.net.wifi.WifiUsabilityStatsEntry.RadioStats[numRadios]; 7417 createNewRadioStatsParcelable(radioStats, s.radioStats); 7418 // TODO: remove the following hardcoded values once if they are removed from public API 7419 return new android.net.wifi.WifiUsabilityStatsEntry(s.timeStampMs, s.rssi, 7420 s.linkSpeedMbps, s.totalTxSuccess, s.totalTxRetries, 7421 s.totalTxBad, s.totalRxSuccess, s.totalRadioOnTimeMs, 7422 s.totalRadioTxTimeMs, s.totalRadioRxTimeMs, s.totalScanTimeMs, 7423 s.totalNanScanTimeMs, s.totalBackgroundScanTimeMs, s.totalRoamScanTimeMs, 7424 s.totalPnoScanTimeMs, s.totalHotspot2ScanTimeMs, s.totalCcaBusyFreqTimeMs, 7425 s.totalRadioOnFreqTimeMs, s.totalBeaconRx, probeStatus, 7426 s.probeElapsedTimeSinceLastUpdateMs, s.probeMcsRateSinceLastUpdate, 7427 s.rxLinkSpeedMbps, s.timeSliceDutyCycleInPercent, contentionTimeStats, rateStats, 7428 radioStats, s.channelUtilizationRatio, s.isThroughputSufficient, 7429 s.isWifiScoringEnabled, s.isCellularDataAvailable, 0, 0, 0, false, 7430 convertLinkStats(stats, info) 7431 ); 7432 } 7433 7434 private void createNewContentionTimeStatsParcelable( 7435 android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats[] statsParcelable, 7436 ContentionTimeStats[] stats) { 7437 if (statsParcelable.length != stats.length || stats.length != NUM_WME_ACCESS_CATEGORIES) { 7438 Log.e(TAG, "The two ContentionTimeStats do not match in length: " 7439 + " in proto: " + stats.length 7440 + " in system API: " + statsParcelable.length); 7441 return; 7442 } 7443 for (int ac = 0; ac < NUM_WME_ACCESS_CATEGORIES; ac++) { 7444 android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats stat = 7445 new android.net.wifi.WifiUsabilityStatsEntry.ContentionTimeStats( 7446 stats[ac].contentionTimeMinMicros, 7447 stats[ac].contentionTimeMaxMicros, 7448 stats[ac].contentionTimeAvgMicros, 7449 stats[ac].contentionNumSamples); 7450 switch (ac) { 7451 case ContentionTimeStats.WME_ACCESS_CATEGORY_BE: 7452 statsParcelable[ 7453 android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_BE] = stat; 7454 break; 7455 case ContentionTimeStats.WME_ACCESS_CATEGORY_BK: 7456 statsParcelable[ 7457 android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_BK] = stat; 7458 break; 7459 case ContentionTimeStats.WME_ACCESS_CATEGORY_VI: 7460 statsParcelable[ 7461 android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_VI] = stat; 7462 break; 7463 case ContentionTimeStats.WME_ACCESS_CATEGORY_VO: 7464 statsParcelable[ 7465 android.net.wifi.WifiUsabilityStatsEntry.WME_ACCESS_CATEGORY_VO] = stat; 7466 break; 7467 default: 7468 Log.e(TAG, "Unknown WME Access Category: " + ac); 7469 } 7470 } 7471 } 7472 7473 private void createNewRateStatsParcelable( 7474 android.net.wifi.WifiUsabilityStatsEntry.RateStats[] statsParcelable, 7475 RateStats[] stats) { 7476 if (stats == null) { 7477 return; 7478 } 7479 for (int i = 0; i < stats.length; i++) { 7480 statsParcelable[i] = new android.net.wifi.WifiUsabilityStatsEntry.RateStats( 7481 convertPreambleTypeEnumToUsabilityStatsType(stats[i].preamble), 7482 convertSpatialStreamEnumToUsabilityStatsType(stats[i].nss), 7483 convertBandwidthEnumToUsabilityStatsType(stats[i].bw), 7484 stats[i].rateMcsIdx, stats[i].bitRateInKbps, stats[i].txMpdu, stats[i].rxMpdu, 7485 stats[i].mpduLost, stats[i].retries 7486 ); 7487 } 7488 } 7489 7490 /** 7491 * Converts bandwidth enum in proto to WifiUsabilityStatsEntry type. 7492 * @param value 7493 */ 7494 @VisibleForTesting 7495 public static int convertBandwidthEnumToUsabilityStatsType(int value) { 7496 switch (value) { 7497 case RateStats.WIFI_BANDWIDTH_20_MHZ: 7498 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_20_MHZ; 7499 case RateStats.WIFI_BANDWIDTH_40_MHZ: 7500 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_40_MHZ; 7501 case RateStats.WIFI_BANDWIDTH_80_MHZ: 7502 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_80_MHZ; 7503 case RateStats.WIFI_BANDWIDTH_160_MHZ: 7504 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_160_MHZ; 7505 case RateStats.WIFI_BANDWIDTH_80P80_MHZ: 7506 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_80P80_MHZ; 7507 case RateStats.WIFI_BANDWIDTH_5_MHZ: 7508 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_5_MHZ; 7509 case RateStats.WIFI_BANDWIDTH_10_MHZ: 7510 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_10_MHZ; 7511 } 7512 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_BANDWIDTH_INVALID; 7513 } 7514 7515 /** 7516 * Converts spatial streams enum in proto to WifiUsabilityStatsEntry type. 7517 * @param value 7518 */ 7519 @VisibleForTesting 7520 public static int convertSpatialStreamEnumToUsabilityStatsType(int value) { 7521 switch (value) { 7522 case RateStats.WIFI_SPATIAL_STREAMS_ONE: 7523 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_SPATIAL_STREAMS_ONE; 7524 case RateStats.WIFI_SPATIAL_STREAMS_TWO: 7525 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_SPATIAL_STREAMS_TWO; 7526 case RateStats.WIFI_SPATIAL_STREAMS_THREE: 7527 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_SPATIAL_STREAMS_THREE; 7528 case RateStats.WIFI_SPATIAL_STREAMS_FOUR: 7529 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_SPATIAL_STREAMS_FOUR; 7530 } 7531 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_SPATIAL_STREAMS_INVALID; 7532 } 7533 7534 /** 7535 * Converts preamble type enum in proto to WifiUsabilityStatsEntry type. 7536 * @param value 7537 */ 7538 @VisibleForTesting 7539 public static int convertPreambleTypeEnumToUsabilityStatsType(int value) { 7540 switch (value) { 7541 case RateStats.WIFI_PREAMBLE_OFDM: 7542 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_PREAMBLE_OFDM; 7543 case RateStats.WIFI_PREAMBLE_CCK: 7544 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_PREAMBLE_CCK; 7545 case RateStats.WIFI_PREAMBLE_HT: 7546 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_PREAMBLE_HT; 7547 case RateStats.WIFI_PREAMBLE_VHT: 7548 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_PREAMBLE_VHT; 7549 case RateStats.WIFI_PREAMBLE_HE: 7550 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_PREAMBLE_HE; 7551 } 7552 return android.net.wifi.WifiUsabilityStatsEntry.WIFI_PREAMBLE_INVALID; 7553 } 7554 7555 private void createNewRadioStatsParcelable( 7556 android.net.wifi.WifiUsabilityStatsEntry.RadioStats[] statsParcelable, 7557 RadioStats[] stats) { 7558 if (stats == null) { 7559 return; 7560 } 7561 for (int i = 0; i < stats.length; i++) { 7562 statsParcelable[i] = 7563 new android.net.wifi.WifiUsabilityStatsEntry.RadioStats( 7564 stats[i].radioId, 7565 stats[i].totalRadioOnTimeMs, 7566 stats[i].totalRadioTxTimeMs, 7567 stats[i].totalRadioRxTimeMs, 7568 stats[i].totalScanTimeMs, 7569 stats[i].totalNanScanTimeMs, 7570 stats[i].totalBackgroundScanTimeMs, 7571 stats[i].totalRoamScanTimeMs, 7572 stats[i].totalPnoScanTimeMs, 7573 stats[i].totalHotspot2ScanTimeMs); 7574 } 7575 } 7576 7577 private WifiUsabilityStatsEntry createNewWifiUsabilityStatsEntry(WifiUsabilityStatsEntry s) { 7578 WifiUsabilityStatsEntry out = new WifiUsabilityStatsEntry(); 7579 out.timeStampMs = s.timeStampMs; 7580 out.totalTxSuccess = s.totalTxSuccess; 7581 out.totalTxRetries = s.totalTxRetries; 7582 out.totalTxBad = s.totalTxBad; 7583 out.totalRxSuccess = s.totalRxSuccess; 7584 out.totalRadioOnTimeMs = s.totalRadioOnTimeMs; 7585 out.totalRadioTxTimeMs = s.totalRadioTxTimeMs; 7586 out.totalRadioRxTimeMs = s.totalRadioRxTimeMs; 7587 out.totalScanTimeMs = s.totalScanTimeMs; 7588 out.totalNanScanTimeMs = s.totalNanScanTimeMs; 7589 out.totalBackgroundScanTimeMs = s.totalBackgroundScanTimeMs; 7590 out.totalRoamScanTimeMs = s.totalRoamScanTimeMs; 7591 out.totalPnoScanTimeMs = s.totalPnoScanTimeMs; 7592 out.totalHotspot2ScanTimeMs = s.totalHotspot2ScanTimeMs; 7593 out.rssi = s.rssi; 7594 out.linkSpeedMbps = s.linkSpeedMbps; 7595 out.totalCcaBusyFreqTimeMs = s.totalCcaBusyFreqTimeMs; 7596 out.totalRadioOnFreqTimeMs = s.totalRadioOnFreqTimeMs; 7597 out.totalBeaconRx = s.totalBeaconRx; 7598 out.wifiScore = s.wifiScore; 7599 out.wifiUsabilityScore = s.wifiUsabilityScore; 7600 out.seqNumToFramework = s.seqNumToFramework; 7601 out.predictionHorizonSec = s.predictionHorizonSec; 7602 out.probeStatusSinceLastUpdate = s.probeStatusSinceLastUpdate; 7603 out.probeElapsedTimeSinceLastUpdateMs = s.probeElapsedTimeSinceLastUpdateMs; 7604 out.probeMcsRateSinceLastUpdate = s.probeMcsRateSinceLastUpdate; 7605 out.rxLinkSpeedMbps = s.rxLinkSpeedMbps; 7606 out.isSameBssidAndFreq = s.isSameBssidAndFreq; 7607 out.seqNumInsideFramework = s.seqNumInsideFramework; 7608 out.deviceMobilityState = s.deviceMobilityState; 7609 out.timeSliceDutyCycleInPercent = s.timeSliceDutyCycleInPercent; 7610 out.contentionTimeStats = s.contentionTimeStats; 7611 out.channelUtilizationRatio = s.channelUtilizationRatio; 7612 out.isThroughputSufficient = s.isThroughputSufficient; 7613 out.isWifiScoringEnabled = s.isWifiScoringEnabled; 7614 out.isCellularDataAvailable = s.isCellularDataAvailable; 7615 out.rateStats = s.rateStats; 7616 out.staCount = s.staCount; 7617 out.channelUtilization = s.channelUtilization; 7618 out.radioStats = s.radioStats; 7619 return out; 7620 } 7621 7622 private WifiUsabilityStats createWifiUsabilityStatsWithLabel(int label, int triggerType, 7623 int firmwareAlertCode) { 7624 WifiUsabilityStats wifiUsabilityStats = new WifiUsabilityStats(); 7625 wifiUsabilityStats.label = label; 7626 wifiUsabilityStats.triggerType = triggerType; 7627 wifiUsabilityStats.firmwareAlertCode = firmwareAlertCode; 7628 wifiUsabilityStats.timeStampMs = mClock.getElapsedSinceBootMillis(); 7629 wifiUsabilityStats.stats = 7630 new WifiUsabilityStatsEntry[mWifiUsabilityStatsEntriesList.size()]; 7631 for (int i = 0; i < mWifiUsabilityStatsEntriesList.size(); i++) { 7632 wifiUsabilityStats.stats[i] = 7633 createNewWifiUsabilityStatsEntry(mWifiUsabilityStatsEntriesList.get(i)); 7634 } 7635 return wifiUsabilityStats; 7636 } 7637 7638 /** 7639 * Label the current snapshot of WifiUsabilityStatsEntrys and save the labeled data in memory. 7640 * @param label WifiUsabilityStats.LABEL_GOOD or WifiUsabilityStats.LABEL_BAD 7641 * @param triggerType what event triggers WifiUsabilityStats 7642 * @param firmwareAlertCode the firmware alert code when the stats was triggered by a 7643 * firmware alert 7644 */ 7645 public void addToWifiUsabilityStatsList(String ifaceName, int label, int triggerType, 7646 int firmwareAlertCode) { 7647 synchronized (mLock) { 7648 if (!isPrimary(ifaceName)) { 7649 return; 7650 } 7651 if (mWifiUsabilityStatsEntriesList.isEmpty() || !mScreenOn) { 7652 return; 7653 } 7654 if (label == WifiUsabilityStats.LABEL_GOOD) { 7655 // Only add a good event if at least |MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS| 7656 // has passed. 7657 if (mWifiUsabilityStatsListGood.isEmpty() 7658 || mWifiUsabilityStatsListGood.getLast().stats[mWifiUsabilityStatsListGood 7659 .getLast().stats.length - 1].timeStampMs 7660 + MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS 7661 < mWifiUsabilityStatsEntriesList.getLast().timeStampMs) { 7662 while (mWifiUsabilityStatsListGood.size() 7663 >= MAX_WIFI_USABILITY_STATS_LIST_SIZE_PER_TYPE) { 7664 mWifiUsabilityStatsListGood.remove( 7665 mRand.nextInt(mWifiUsabilityStatsListGood.size())); 7666 } 7667 mWifiUsabilityStatsListGood.add( 7668 createWifiUsabilityStatsWithLabel(label, triggerType, 7669 firmwareAlertCode)); 7670 } 7671 } else { 7672 // Only add a bad event if at least |MIN_DATA_STALL_WAIT_MS| 7673 // has passed. 7674 mScoreBreachLowTimeMillis = -1; 7675 if (mWifiUsabilityStatsListBad.isEmpty() 7676 || (mWifiUsabilityStatsListBad.getLast().stats[mWifiUsabilityStatsListBad 7677 .getLast().stats.length - 1].timeStampMs 7678 + MIN_DATA_STALL_WAIT_MS 7679 < mWifiUsabilityStatsEntriesList.getLast().timeStampMs)) { 7680 while (mWifiUsabilityStatsListBad.size() 7681 >= MAX_WIFI_USABILITY_STATS_LIST_SIZE_PER_TYPE) { 7682 mWifiUsabilityStatsListBad.remove( 7683 mRand.nextInt(mWifiUsabilityStatsListBad.size())); 7684 } 7685 mWifiUsabilityStatsListBad.add( 7686 createWifiUsabilityStatsWithLabel(label, triggerType, 7687 firmwareAlertCode)); 7688 } 7689 } 7690 mWifiUsabilityStatsCounter = 0; 7691 mWifiUsabilityStatsEntriesList.clear(); 7692 } 7693 } 7694 7695 private DeviceMobilityStatePnoScanStats getOrCreateDeviceMobilityStatePnoScanStats( 7696 @DeviceMobilityState int deviceMobilityState) { 7697 DeviceMobilityStatePnoScanStats stats = mMobilityStatePnoStatsMap.get(deviceMobilityState); 7698 if (stats == null) { 7699 stats = new DeviceMobilityStatePnoScanStats(); 7700 stats.deviceMobilityState = deviceMobilityState; 7701 stats.numTimesEnteredState = 0; 7702 stats.totalDurationMs = 0; 7703 stats.pnoDurationMs = 0; 7704 mMobilityStatePnoStatsMap.put(deviceMobilityState, stats); 7705 } 7706 return stats; 7707 } 7708 7709 /** 7710 * Updates the current device mobility state's total duration. This method should be called 7711 * before entering a new device mobility state. 7712 */ 7713 private void updateCurrentMobilityStateTotalDuration(long now) { 7714 DeviceMobilityStatePnoScanStats stats = 7715 getOrCreateDeviceMobilityStatePnoScanStats(mCurrentDeviceMobilityState); 7716 stats.totalDurationMs += now - mCurrentDeviceMobilityStateStartMs; 7717 mCurrentDeviceMobilityStateStartMs = now; 7718 } 7719 7720 /** 7721 * Convert the IntCounter of passpoint profile types and counts to proto's 7722 * repeated IntKeyVal array. 7723 * 7724 * @param passpointProfileTypes passpoint profile types and counts. 7725 */ 7726 private PasspointProfileTypeCount[] convertPasspointProfilesToProto( 7727 IntCounter passpointProfileTypes) { 7728 return passpointProfileTypes.toProto(PasspointProfileTypeCount.class, (key, count) -> { 7729 PasspointProfileTypeCount entry = new PasspointProfileTypeCount(); 7730 entry.eapMethodType = key; 7731 entry.count = count; 7732 return entry; 7733 }); 7734 } 7735 7736 /** 7737 * Reports that the device entered a new mobility state. 7738 * 7739 * @param newState the new device mobility state. 7740 */ 7741 public void enterDeviceMobilityState(@DeviceMobilityState int newState) { 7742 synchronized (mLock) { 7743 long now = mClock.getElapsedSinceBootMillis(); 7744 updateCurrentMobilityStateTotalDuration(now); 7745 7746 if (newState == mCurrentDeviceMobilityState) return; 7747 7748 mCurrentDeviceMobilityState = newState; 7749 DeviceMobilityStatePnoScanStats stats = 7750 getOrCreateDeviceMobilityStatePnoScanStats(mCurrentDeviceMobilityState); 7751 stats.numTimesEnteredState++; 7752 } 7753 } 7754 7755 /** 7756 * Logs the start of a PNO scan. 7757 */ 7758 public void logPnoScanStart() { 7759 synchronized (mLock) { 7760 long now = mClock.getElapsedSinceBootMillis(); 7761 mCurrentDeviceMobilityStatePnoScanStartMs = now; 7762 updateCurrentMobilityStateTotalDuration(now); 7763 } 7764 } 7765 7766 /** 7767 * Logs the end of a PNO scan. This is attributed to the current device mobility state, as 7768 * logged by {@link #enterDeviceMobilityState(int)}. Thus, if the mobility state changes during 7769 * a PNO scan, one should call {@link #logPnoScanStop()}, {@link #enterDeviceMobilityState(int)} 7770 * , then {@link #logPnoScanStart()} so that the portion of PNO scan before the mobility state 7771 * change can be correctly attributed to the previous mobility state. 7772 */ 7773 public void logPnoScanStop() { 7774 synchronized (mLock) { 7775 if (mCurrentDeviceMobilityStatePnoScanStartMs < 0) { 7776 Log.e(TAG, "Called WifiMetrics#logPNoScanStop() without calling " 7777 + "WifiMetrics#logPnoScanStart() first!"); 7778 return; 7779 } 7780 DeviceMobilityStatePnoScanStats stats = 7781 getOrCreateDeviceMobilityStatePnoScanStats(mCurrentDeviceMobilityState); 7782 long now = mClock.getElapsedSinceBootMillis(); 7783 stats.pnoDurationMs += now - mCurrentDeviceMobilityStatePnoScanStartMs; 7784 mCurrentDeviceMobilityStatePnoScanStartMs = -1; 7785 updateCurrentMobilityStateTotalDuration(now); 7786 } 7787 } 7788 7789 /** 7790 * Logs that wifi bug report is taken 7791 */ 7792 public void logBugReport() { 7793 synchronized (mLock) { 7794 for (ConnectionEvent connectionEvent : mCurrentConnectionEventPerIface.values()) { 7795 if (connectionEvent != null) { 7796 connectionEvent.mConnectionEvent.automaticBugReportTaken = true; 7797 } 7798 } 7799 } 7800 } 7801 7802 /** 7803 * Add a new listener for Wi-Fi usability stats handling. 7804 */ 7805 public void addOnWifiUsabilityListener(@NonNull IOnWifiUsabilityStatsListener listener) { 7806 if (!mOnWifiUsabilityListeners.register(listener)) { 7807 Log.e(TAG, "Failed to add listener"); 7808 return; 7809 } 7810 if (DBG) { 7811 Log.v(TAG, "Adding listener. Num listeners: " 7812 + mOnWifiUsabilityListeners.getRegisteredCallbackCount()); 7813 } 7814 } 7815 7816 /** 7817 * Remove an existing listener for Wi-Fi usability stats handling. 7818 */ 7819 public void removeOnWifiUsabilityListener(@NonNull IOnWifiUsabilityStatsListener listener) { 7820 mOnWifiUsabilityListeners.unregister(listener); 7821 if (DBG) { 7822 Log.v(TAG, "Removing listener. Num listeners: " 7823 + mOnWifiUsabilityListeners.getRegisteredCallbackCount()); 7824 } 7825 } 7826 7827 /** 7828 * Updates the Wi-Fi usability score and increments occurence of a particular Wifi usability 7829 * score passed in from outside framework. Scores are bounded within 7830 * [MIN_WIFI_USABILITY_SCORE, MAX_WIFI_USABILITY_SCORE]. 7831 * 7832 * Also records events when the Wifi usability score breaches significant thresholds. 7833 * 7834 * @param seqNum Sequence number of the Wi-Fi usability score. 7835 * @param score The Wi-Fi usability score. 7836 * @param predictionHorizonSec Prediction horizon of the Wi-Fi usability score. 7837 */ 7838 public void incrementWifiUsabilityScoreCount(String ifaceName, int seqNum, int score, 7839 int predictionHorizonSec) { 7840 if (score < MIN_WIFI_USABILITY_SCORE || score > MAX_WIFI_USABILITY_SCORE) { 7841 return; 7842 } 7843 synchronized (mLock) { 7844 mSeqNumToFramework = seqNum; 7845 mLastWifiUsabilityScore = score; 7846 mLastWifiUsabilityScoreNoReset = score; 7847 mWifiUsabilityScoreCounts.put(score, mWifiUsabilityScoreCounts.get(score) + 1); 7848 mLastPredictionHorizonSec = predictionHorizonSec; 7849 mLastPredictionHorizonSecNoReset = predictionHorizonSec; 7850 7851 boolean wifiWins = mWifiWinsUsabilityScore; 7852 if (score > LOW_WIFI_USABILITY_SCORE) { 7853 wifiWins = true; 7854 } else if (score < LOW_WIFI_USABILITY_SCORE) { 7855 wifiWins = false; 7856 } 7857 7858 if (wifiWins != mWifiWinsUsabilityScore) { 7859 mWifiWinsUsabilityScore = wifiWins; 7860 StaEvent event = new StaEvent(); 7861 event.type = StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH; 7862 addStaEvent(ifaceName, event); 7863 // Only record the first score breach by checking whether mScoreBreachLowTimeMillis 7864 // has been set to -1 7865 if (!wifiWins && mScoreBreachLowTimeMillis == -1) { 7866 mScoreBreachLowTimeMillis = mClock.getElapsedSinceBootMillis(); 7867 } 7868 } 7869 } 7870 } 7871 7872 /** 7873 * Reports stats for a successful link probe. 7874 * 7875 * @param timeSinceLastTxSuccessMs At {@code startTimestampMs}, the number of milliseconds since 7876 * the last Tx success (according to 7877 * {@link WifiInfo#txSuccess}). 7878 * @param rssi The Rx RSSI at {@code startTimestampMs}. 7879 * @param linkSpeed The Tx link speed in Mbps at {@code startTimestampMs}. 7880 * @param elapsedTimeMs The number of milliseconds between when the command to transmit the 7881 * probe was sent to the driver and when the driver responded that the 7882 * probe was ACKed. Note: this number should be correlated with the number 7883 * of retries that the driver attempted before the probe was ACKed. 7884 */ 7885 public void logLinkProbeSuccess(String ifaceName, long timeSinceLastTxSuccessMs, 7886 int rssi, int linkSpeed, int elapsedTimeMs) { 7887 synchronized (mLock) { 7888 mProbeStatusSinceLastUpdate = 7889 android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_SUCCESS; 7890 mProbeElapsedTimeSinceLastUpdateMs = elapsedTimeMs; 7891 7892 mLinkProbeSuccessSecondsSinceLastTxSuccessHistogram.increment( 7893 (int) (timeSinceLastTxSuccessMs / 1000)); 7894 mLinkProbeSuccessRssiCounts.increment(rssi); 7895 mLinkProbeSuccessLinkSpeedCounts.increment(linkSpeed); 7896 mLinkProbeSuccessElapsedTimeMsHistogram.increment(elapsedTimeMs); 7897 7898 if (mLinkProbeStaEventCount < MAX_LINK_PROBE_STA_EVENTS) { 7899 StaEvent event = new StaEvent(); 7900 event.type = StaEvent.TYPE_LINK_PROBE; 7901 event.linkProbeWasSuccess = true; 7902 event.linkProbeSuccessElapsedTimeMs = elapsedTimeMs; 7903 addStaEvent(ifaceName, event); 7904 } 7905 mLinkProbeStaEventCount++; 7906 } 7907 } 7908 7909 /** 7910 * Reports stats for an unsuccessful link probe. 7911 * 7912 * @param timeSinceLastTxSuccessMs At {@code startTimestampMs}, the number of milliseconds since 7913 * the last Tx success (according to 7914 * {@link WifiInfo#txSuccess}). 7915 * @param rssi The Rx RSSI at {@code startTimestampMs}. 7916 * @param linkSpeed The Tx link speed in Mbps at {@code startTimestampMs}. 7917 * @param reason The error code for the failure. See 7918 * {@link WifiNl80211Manager.SendMgmtFrameError}. 7919 */ 7920 public void logLinkProbeFailure(String ifaceName, long timeSinceLastTxSuccessMs, 7921 int rssi, int linkSpeed, int reason) { 7922 synchronized (mLock) { 7923 mProbeStatusSinceLastUpdate = 7924 android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_FAILURE; 7925 mProbeElapsedTimeSinceLastUpdateMs = Integer.MAX_VALUE; 7926 7927 mLinkProbeFailureSecondsSinceLastTxSuccessHistogram.increment( 7928 (int) (timeSinceLastTxSuccessMs / 1000)); 7929 mLinkProbeFailureRssiCounts.increment(rssi); 7930 mLinkProbeFailureLinkSpeedCounts.increment(linkSpeed); 7931 mLinkProbeFailureReasonCounts.increment(reason); 7932 7933 if (mLinkProbeStaEventCount < MAX_LINK_PROBE_STA_EVENTS) { 7934 StaEvent event = new StaEvent(); 7935 event.type = StaEvent.TYPE_LINK_PROBE; 7936 event.linkProbeWasSuccess = false; 7937 event.linkProbeFailureReason = linkProbeFailureReasonToProto(reason); 7938 addStaEvent(ifaceName, event); 7939 } 7940 mLinkProbeStaEventCount++; 7941 } 7942 } 7943 7944 /** 7945 * Increments the number of probes triggered by the experiment `experimentId`. 7946 */ 7947 public void incrementLinkProbeExperimentProbeCount(String experimentId) { 7948 synchronized (mLock) { 7949 mLinkProbeExperimentProbeCounts.increment(experimentId); 7950 } 7951 } 7952 7953 /** 7954 * Update wifi config store read duration. 7955 * 7956 * @param timeMs Time it took to complete the operation, in milliseconds 7957 */ 7958 public void noteWifiConfigStoreReadDuration(int timeMs) { 7959 synchronized (mLock) { 7960 MetricsUtils.addValueToLinearHistogram(timeMs, mWifiConfigStoreReadDurationHistogram, 7961 WIFI_CONFIG_STORE_IO_DURATION_BUCKET_RANGES_MS); 7962 } 7963 } 7964 7965 /** 7966 * Update wifi config store write duration. 7967 * 7968 * @param timeMs Time it took to complete the operation, in milliseconds 7969 */ 7970 public void noteWifiConfigStoreWriteDuration(int timeMs) { 7971 synchronized (mLock) { 7972 MetricsUtils.addValueToLinearHistogram(timeMs, mWifiConfigStoreWriteDurationHistogram, 7973 WIFI_CONFIG_STORE_IO_DURATION_BUCKET_RANGES_MS); 7974 } 7975 } 7976 7977 /** 7978 * Logs the decision of a network selection algorithm when compared against another network 7979 * selection algorithm. 7980 * 7981 * @param experiment1Id ID of one experiment 7982 * @param experiment2Id ID of the other experiment 7983 * @param isSameDecision did the 2 experiments make the same decision? 7984 * @param numNetworkChoices the number of non-null network choices there were, where the null 7985 * choice is not selecting any network 7986 */ 7987 public void logNetworkSelectionDecision(int experiment1Id, int experiment2Id, 7988 boolean isSameDecision, int numNetworkChoices) { 7989 if (numNetworkChoices < 0) { 7990 Log.e(TAG, "numNetworkChoices cannot be negative!"); 7991 return; 7992 } 7993 if (experiment1Id == experiment2Id) { 7994 Log.e(TAG, "comparing the same experiment id: " + experiment1Id); 7995 return; 7996 } 7997 7998 Pair<Integer, Integer> key = new Pair<>(experiment1Id, experiment2Id); 7999 synchronized (mLock) { 8000 NetworkSelectionExperimentResults results = 8001 mNetworkSelectionExperimentPairNumChoicesCounts 8002 .computeIfAbsent(key, k -> new NetworkSelectionExperimentResults()); 8003 8004 IntCounter counter = isSameDecision 8005 ? results.sameSelectionNumChoicesCounter 8006 : results.differentSelectionNumChoicesCounter; 8007 8008 counter.increment(numNetworkChoices); 8009 } 8010 } 8011 8012 /** Increment number of network request API usage stats */ 8013 public void incrementNetworkRequestApiNumRequest() { 8014 synchronized (mLock) { 8015 mWifiNetworkRequestApiLog.numRequest++; 8016 } 8017 } 8018 8019 /** Add to the network request API match size histogram */ 8020 public void incrementNetworkRequestApiMatchSizeHistogram(int matchSize) { 8021 synchronized (mLock) { 8022 mWifiNetworkRequestApiMatchSizeHistogram.increment(matchSize); 8023 } 8024 } 8025 8026 /** Increment number of connection success on primary iface via network request API */ 8027 public void incrementNetworkRequestApiNumConnectSuccessOnPrimaryIface() { 8028 synchronized (mLock) { 8029 mWifiNetworkRequestApiLog.numConnectSuccessOnPrimaryIface++; 8030 } 8031 } 8032 8033 /** Increment number of requests that bypassed user approval via network request API */ 8034 public void incrementNetworkRequestApiNumUserApprovalBypass() { 8035 synchronized (mLock) { 8036 mWifiNetworkRequestApiLog.numUserApprovalBypass++; 8037 } 8038 } 8039 8040 /** Increment number of requests that user rejected via network request API */ 8041 public void incrementNetworkRequestApiNumUserReject() { 8042 synchronized (mLock) { 8043 mWifiNetworkRequestApiLog.numUserReject++; 8044 } 8045 } 8046 8047 /** Increment number of requests from unique apps via network request API */ 8048 public void incrementNetworkRequestApiNumApps() { 8049 synchronized (mLock) { 8050 mWifiNetworkRequestApiLog.numApps++; 8051 } 8052 } 8053 8054 /** Add to the network request API connection duration histogram */ 8055 public void incrementNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram( 8056 int durationSec) { 8057 synchronized (mLock) { 8058 mWifiNetworkRequestApiConnectionDurationSecOnPrimaryIfaceHistogram.increment( 8059 durationSec); 8060 } 8061 } 8062 8063 /** Add to the network request API connection duration on secondary iface histogram */ 8064 public void incrementNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram( 8065 int durationSec) { 8066 synchronized (mLock) { 8067 mWifiNetworkRequestApiConnectionDurationSecOnSecondaryIfaceHistogram.increment( 8068 durationSec); 8069 } 8070 } 8071 8072 /** Increment number of connection on primary iface via network request API */ 8073 public void incrementNetworkRequestApiNumConnectOnPrimaryIface() { 8074 synchronized (mLock) { 8075 mWifiNetworkRequestApiLog.numConnectOnPrimaryIface++; 8076 } 8077 } 8078 8079 /** Increment number of connection on secondary iface via network request API */ 8080 public void incrementNetworkRequestApiNumConnectOnSecondaryIface() { 8081 synchronized (mLock) { 8082 mWifiNetworkRequestApiLog.numConnectOnSecondaryIface++; 8083 } 8084 } 8085 8086 /** Increment number of connection success on secondary iface via network request API */ 8087 public void incrementNetworkRequestApiNumConnectSuccessOnSecondaryIface() { 8088 synchronized (mLock) { 8089 mWifiNetworkRequestApiLog.numConnectSuccessOnSecondaryIface++; 8090 } 8091 } 8092 8093 /** Increment number of concurrent connection via network request API */ 8094 public void incrementNetworkRequestApiNumConcurrentConnection() { 8095 synchronized (mLock) { 8096 mWifiNetworkRequestApiLog.numConcurrentConnection++; 8097 } 8098 } 8099 8100 /** Add to the network request API concurrent connection duration histogram */ 8101 public void incrementNetworkRequestApiConcurrentConnectionDurationSecHistogram( 8102 int durationSec) { 8103 synchronized (mLock) { 8104 mWifiNetworkRequestApiConcurrentConnectionDurationSecHistogram.increment( 8105 durationSec); 8106 } 8107 } 8108 8109 /** Increment number of network suggestion API modification by app stats */ 8110 public void incrementNetworkSuggestionApiNumModification() { 8111 synchronized (mLock) { 8112 mWifiNetworkSuggestionApiLog.numModification++; 8113 } 8114 } 8115 8116 /** Increment number of connection success via network suggestion API */ 8117 public void incrementNetworkSuggestionApiNumConnectSuccess() { 8118 synchronized (mLock) { 8119 mWifiNetworkSuggestionApiLog.numConnectSuccess++; 8120 } 8121 } 8122 8123 /** Increment number of connection failure via network suggestion API */ 8124 public void incrementNetworkSuggestionApiNumConnectFailure() { 8125 synchronized (mLock) { 8126 mWifiNetworkSuggestionApiLog.numConnectFailure++; 8127 } 8128 } 8129 8130 /** Increment number of user revoke suggestion permission. Including from settings or 8131 * disallowed from UI. 8132 */ 8133 public void incrementNetworkSuggestionUserRevokePermission() { 8134 synchronized (mLock) { 8135 mWifiNetworkSuggestionApiLog.userRevokeAppSuggestionPermission++; 8136 } 8137 } 8138 8139 /** 8140 * Increment number of times a ScanResult matches more than one WifiNetworkSuggestion. 8141 */ 8142 public void incrementNetworkSuggestionMoreThanOneSuggestionForSingleScanResult() { 8143 synchronized (mLock) { 8144 mWifiNetworkSuggestionApiLog.numMultipleSuggestions++; 8145 } 8146 } 8147 8148 /** 8149 * Add a saved network which has at least has one suggestion for same network on the device. 8150 */ 8151 public void addSuggestionExistsForSavedNetwork(String key) { 8152 synchronized (mLock) { 8153 mWifiNetworkSuggestionCoexistSavedNetworks.add(key); 8154 } 8155 } 8156 8157 /** 8158 * Add a priority group which is using on the device.(Except default priority group). 8159 */ 8160 public void addNetworkSuggestionPriorityGroup(int priorityGroup) { 8161 synchronized (mLock) { 8162 // Ignore the default group 8163 if (priorityGroup == 0) { 8164 return; 8165 } 8166 mWifiNetworkSuggestionPriorityGroups.put(priorityGroup, true); 8167 } 8168 8169 } 8170 8171 /** Clear and set the latest network suggestion API max list size histogram */ 8172 public void noteNetworkSuggestionApiListSizeHistogram(List<Integer> listSizes) { 8173 synchronized (mLock) { 8174 mWifiNetworkSuggestionApiListSizeHistogram.clear(); 8175 for (Integer listSize : listSizes) { 8176 mWifiNetworkSuggestionApiListSizeHistogram.increment(listSize); 8177 } 8178 } 8179 } 8180 8181 /** Increment number of app add suggestion with different privilege */ 8182 public void incrementNetworkSuggestionApiUsageNumOfAppInType(int appType) { 8183 int typeCode; 8184 synchronized (mLock) { 8185 switch (appType) { 8186 case WifiNetworkSuggestionsManager.APP_TYPE_CARRIER_PRIVILEGED: 8187 typeCode = WifiNetworkSuggestionApiLog.TYPE_CARRIER_PRIVILEGED; 8188 break; 8189 case WifiNetworkSuggestionsManager.APP_TYPE_NETWORK_PROVISIONING: 8190 typeCode = WifiNetworkSuggestionApiLog.TYPE_NETWORK_PROVISIONING; 8191 break; 8192 case WifiNetworkSuggestionsManager.APP_TYPE_NON_PRIVILEGED: 8193 typeCode = WifiNetworkSuggestionApiLog.TYPE_NON_PRIVILEGED; 8194 break; 8195 default: 8196 typeCode = WifiNetworkSuggestionApiLog.TYPE_UNKNOWN; 8197 } 8198 mWifiNetworkSuggestionApiAppTypeCounter.increment(typeCode); 8199 } 8200 } 8201 8202 /** Add user action to the approval suggestion app UI */ 8203 public void addUserApprovalSuggestionAppUiReaction(@WifiNetworkSuggestionsManager.UserActionCode 8204 int actionType, boolean isDialog) { 8205 int actionCode; 8206 switch (actionType) { 8207 case WifiNetworkSuggestionsManager.ACTION_USER_ALLOWED_APP: 8208 actionCode = UserReactionToApprovalUiEvent.ACTION_ALLOWED; 8209 break; 8210 case WifiNetworkSuggestionsManager.ACTION_USER_DISALLOWED_APP: 8211 actionCode = UserReactionToApprovalUiEvent.ACTION_DISALLOWED; 8212 break; 8213 case WifiNetworkSuggestionsManager.ACTION_USER_DISMISS: 8214 actionCode = UserReactionToApprovalUiEvent.ACTION_DISMISS; 8215 break; 8216 default: 8217 actionCode = UserReactionToApprovalUiEvent.ACTION_UNKNOWN; 8218 } 8219 UserReaction event = new UserReaction(); 8220 event.userAction = actionCode; 8221 event.isDialog = isDialog; 8222 synchronized (mLock) { 8223 mUserApprovalSuggestionAppUiReactionList.add(event); 8224 } 8225 } 8226 8227 /** Add user action to the approval Carrier Imsi protection exemption UI */ 8228 public void addUserApprovalCarrierUiReaction(@WifiCarrierInfoManager.UserActionCode 8229 int actionType, boolean isDialog) { 8230 int actionCode; 8231 switch (actionType) { 8232 case WifiCarrierInfoManager.ACTION_USER_ALLOWED_CARRIER: 8233 actionCode = UserReactionToApprovalUiEvent.ACTION_ALLOWED; 8234 break; 8235 case WifiCarrierInfoManager.ACTION_USER_DISALLOWED_CARRIER: 8236 actionCode = UserReactionToApprovalUiEvent.ACTION_DISALLOWED; 8237 break; 8238 case WifiCarrierInfoManager.ACTION_USER_DISMISS: 8239 actionCode = UserReactionToApprovalUiEvent.ACTION_DISMISS; 8240 break; 8241 default: 8242 actionCode = UserReactionToApprovalUiEvent.ACTION_UNKNOWN; 8243 } 8244 UserReaction event = new UserReaction(); 8245 event.userAction = actionCode; 8246 event.isDialog = isDialog; 8247 8248 synchronized (mLock) { 8249 mUserApprovalCarrierUiReactionList.add(event); 8250 } 8251 } 8252 8253 /** 8254 * Sets the nominator for a network (i.e. which entity made the suggestion to connect) 8255 * @param networkId the ID of the network, from its {@link WifiConfiguration} 8256 * @param nominatorId the entity that made the suggestion to connect to this network, 8257 * from {@link WifiMetricsProto.ConnectionEvent.ConnectionNominator} 8258 */ 8259 public void setNominatorForNetwork(int networkId, int nominatorId) { 8260 synchronized (mLock) { 8261 if (networkId == WifiConfiguration.INVALID_NETWORK_ID) return; 8262 mNetworkIdToNominatorId.put(networkId, nominatorId); 8263 8264 // user connect choice is preventing switching off from the connected network 8265 if (nominatorId 8266 == WifiMetricsProto.ConnectionEvent.NOMINATOR_SAVED_USER_CONNECT_CHOICE 8267 && mWifiStatusBuilder.getNetworkId() == networkId) { 8268 mWifiStatusBuilder.setUserChoice(true); 8269 } 8270 } 8271 } 8272 8273 /** 8274 * Sets the numeric CandidateScorer id. 8275 */ 8276 public void setNetworkSelectorExperimentId(int expId) { 8277 synchronized (mLock) { 8278 mNetworkSelectorExperimentId = expId; 8279 } 8280 } 8281 8282 /** Add a WifiLock acquisition session */ 8283 public void addWifiLockAcqSession(int lockType, int[] attrUids, String[] attrTags, 8284 int callerType, long duration, boolean isPowersaveDisableAllowed, 8285 boolean isAppExemptedFromScreenOn, boolean isAppExemptedFromForeground) { 8286 int lockMode; 8287 switch (lockType) { 8288 case WifiManager.WIFI_MODE_FULL_HIGH_PERF: 8289 mWifiLockHighPerfAcqDurationSecHistogram.increment((int) (duration / 1000)); 8290 lockMode = WifiStatsLog.WIFI_LOCK_RELEASED__MODE__WIFI_MODE_FULL_HIGH_PERF; 8291 break; 8292 8293 case WifiManager.WIFI_MODE_FULL_LOW_LATENCY: 8294 mWifiLockLowLatencyAcqDurationSecHistogram.increment((int) (duration / 1000)); 8295 lockMode = WifiStatsLog.WIFI_LOCK_RELEASED__MODE__WIFI_MODE_FULL_LOW_LATENCY; 8296 break; 8297 default: 8298 Log.e(TAG, "addWifiLockAcqSession: Invalid lock type: " + lockType); 8299 return; 8300 } 8301 WifiStatsLog.write(WifiStatsLog.WIFI_LOCK_RELEASED, 8302 attrUids, 8303 attrTags, 8304 callerType, 8305 lockMode, 8306 duration, 8307 isPowersaveDisableAllowed, 8308 isAppExemptedFromScreenOn, 8309 isAppExemptedFromForeground); 8310 } 8311 8312 /** Add a WifiLock active session */ 8313 public void addWifiLockActiveSession(int lockType, int[] attrUids, String[] attrTags, 8314 long duration, boolean isPowersaveDisableAllowed, 8315 boolean isAppExemptedFromScreenOn, boolean isAppExemptedFromForeground) { 8316 int lockMode; 8317 switch (lockType) { 8318 case WifiManager.WIFI_MODE_FULL_HIGH_PERF: 8319 lockMode = WifiStatsLog.WIFI_LOCK_DEACTIVATED__MODE__WIFI_MODE_FULL_HIGH_PERF; 8320 mWifiLockStats.highPerfActiveTimeMs += duration; 8321 mWifiLockHighPerfActiveSessionDurationSecHistogram.increment( 8322 (int) (duration / 1000)); 8323 break; 8324 8325 case WifiManager.WIFI_MODE_FULL_LOW_LATENCY: 8326 lockMode = WifiStatsLog.WIFI_LOCK_DEACTIVATED__MODE__WIFI_MODE_FULL_LOW_LATENCY; 8327 mWifiLockStats.lowLatencyActiveTimeMs += duration; 8328 mWifiLockLowLatencyActiveSessionDurationSecHistogram.increment( 8329 (int) (duration / 1000)); 8330 break; 8331 8332 default: 8333 Log.e(TAG, "addWifiLockActiveSession: Invalid lock type: " + lockType); 8334 return; 8335 } 8336 WifiStatsLog.write(WifiStatsLog.WIFI_LOCK_DEACTIVATED, 8337 attrUids, 8338 attrTags, 8339 lockMode, 8340 duration, 8341 isPowersaveDisableAllowed, 8342 isAppExemptedFromScreenOn, 8343 isAppExemptedFromForeground); 8344 } 8345 8346 /** Increments metrics counting number of addOrUpdateNetwork calls. **/ 8347 public void incrementNumAddOrUpdateNetworkCalls() { 8348 synchronized (mLock) { 8349 mWifiLogProto.numAddOrUpdateNetworkCalls++; 8350 } 8351 } 8352 8353 /** Increments metrics counting number of enableNetwork calls. **/ 8354 public void incrementNumEnableNetworkCalls() { 8355 synchronized (mLock) { 8356 mWifiLogProto.numEnableNetworkCalls++; 8357 } 8358 } 8359 8360 /** Add to WifiToggleStats **/ 8361 public void incrementNumWifiToggles(boolean isPrivileged, boolean enable) { 8362 synchronized (mLock) { 8363 if (isPrivileged && enable) { 8364 mWifiToggleStats.numToggleOnPrivileged++; 8365 } else if (isPrivileged && !enable) { 8366 mWifiToggleStats.numToggleOffPrivileged++; 8367 } else if (!isPrivileged && enable) { 8368 mWifiToggleStats.numToggleOnNormal++; 8369 } else { 8370 mWifiToggleStats.numToggleOffNormal++; 8371 } 8372 } 8373 } 8374 8375 /** 8376 * Increment number of passpoint provision failure 8377 * @param failureCode indicates error condition 8378 */ 8379 public void incrementPasspointProvisionFailure(@OsuFailure int failureCode) { 8380 int provisionFailureCode; 8381 synchronized (mLock) { 8382 switch (failureCode) { 8383 case ProvisioningCallback.OSU_FAILURE_AP_CONNECTION: 8384 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_AP_CONNECTION; 8385 break; 8386 case ProvisioningCallback.OSU_FAILURE_SERVER_URL_INVALID: 8387 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_SERVER_URL_INVALID; 8388 break; 8389 case ProvisioningCallback.OSU_FAILURE_SERVER_CONNECTION: 8390 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_SERVER_CONNECTION; 8391 break; 8392 case ProvisioningCallback.OSU_FAILURE_SERVER_VALIDATION: 8393 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_SERVER_VALIDATION; 8394 break; 8395 case ProvisioningCallback.OSU_FAILURE_SERVICE_PROVIDER_VERIFICATION: 8396 provisionFailureCode = PasspointProvisionStats 8397 .OSU_FAILURE_SERVICE_PROVIDER_VERIFICATION; 8398 break; 8399 case ProvisioningCallback.OSU_FAILURE_PROVISIONING_ABORTED: 8400 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_PROVISIONING_ABORTED; 8401 break; 8402 case ProvisioningCallback.OSU_FAILURE_PROVISIONING_NOT_AVAILABLE: 8403 provisionFailureCode = PasspointProvisionStats 8404 .OSU_FAILURE_PROVISIONING_NOT_AVAILABLE; 8405 break; 8406 case ProvisioningCallback.OSU_FAILURE_INVALID_URL_FORMAT_FOR_OSU: 8407 provisionFailureCode = PasspointProvisionStats 8408 .OSU_FAILURE_INVALID_URL_FORMAT_FOR_OSU; 8409 break; 8410 case ProvisioningCallback.OSU_FAILURE_UNEXPECTED_COMMAND_TYPE: 8411 provisionFailureCode = PasspointProvisionStats 8412 .OSU_FAILURE_UNEXPECTED_COMMAND_TYPE; 8413 break; 8414 case ProvisioningCallback.OSU_FAILURE_UNEXPECTED_SOAP_MESSAGE_TYPE: 8415 provisionFailureCode = PasspointProvisionStats 8416 .OSU_FAILURE_UNEXPECTED_SOAP_MESSAGE_TYPE; 8417 break; 8418 case ProvisioningCallback.OSU_FAILURE_SOAP_MESSAGE_EXCHANGE: 8419 provisionFailureCode = PasspointProvisionStats 8420 .OSU_FAILURE_SOAP_MESSAGE_EXCHANGE; 8421 break; 8422 case ProvisioningCallback.OSU_FAILURE_START_REDIRECT_LISTENER: 8423 provisionFailureCode = PasspointProvisionStats 8424 .OSU_FAILURE_START_REDIRECT_LISTENER; 8425 break; 8426 case ProvisioningCallback.OSU_FAILURE_TIMED_OUT_REDIRECT_LISTENER: 8427 provisionFailureCode = PasspointProvisionStats 8428 .OSU_FAILURE_TIMED_OUT_REDIRECT_LISTENER; 8429 break; 8430 case ProvisioningCallback.OSU_FAILURE_NO_OSU_ACTIVITY_FOUND: 8431 provisionFailureCode = PasspointProvisionStats 8432 .OSU_FAILURE_NO_OSU_ACTIVITY_FOUND; 8433 break; 8434 case ProvisioningCallback.OSU_FAILURE_UNEXPECTED_SOAP_MESSAGE_STATUS: 8435 provisionFailureCode = PasspointProvisionStats 8436 .OSU_FAILURE_UNEXPECTED_SOAP_MESSAGE_STATUS; 8437 break; 8438 case ProvisioningCallback.OSU_FAILURE_NO_PPS_MO: 8439 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_NO_PPS_MO; 8440 break; 8441 case ProvisioningCallback.OSU_FAILURE_NO_AAA_SERVER_TRUST_ROOT_NODE: 8442 provisionFailureCode = PasspointProvisionStats 8443 .OSU_FAILURE_NO_AAA_SERVER_TRUST_ROOT_NODE; 8444 break; 8445 case ProvisioningCallback.OSU_FAILURE_NO_REMEDIATION_SERVER_TRUST_ROOT_NODE: 8446 provisionFailureCode = PasspointProvisionStats 8447 .OSU_FAILURE_NO_REMEDIATION_SERVER_TRUST_ROOT_NODE; 8448 break; 8449 case ProvisioningCallback.OSU_FAILURE_NO_POLICY_SERVER_TRUST_ROOT_NODE: 8450 provisionFailureCode = PasspointProvisionStats 8451 .OSU_FAILURE_NO_POLICY_SERVER_TRUST_ROOT_NODE; 8452 break; 8453 case ProvisioningCallback.OSU_FAILURE_RETRIEVE_TRUST_ROOT_CERTIFICATES: 8454 provisionFailureCode = PasspointProvisionStats 8455 .OSU_FAILURE_RETRIEVE_TRUST_ROOT_CERTIFICATES; 8456 break; 8457 case ProvisioningCallback.OSU_FAILURE_NO_AAA_TRUST_ROOT_CERTIFICATE: 8458 provisionFailureCode = PasspointProvisionStats 8459 .OSU_FAILURE_NO_AAA_TRUST_ROOT_CERTIFICATE; 8460 break; 8461 case ProvisioningCallback.OSU_FAILURE_ADD_PASSPOINT_CONFIGURATION: 8462 provisionFailureCode = PasspointProvisionStats 8463 .OSU_FAILURE_ADD_PASSPOINT_CONFIGURATION; 8464 break; 8465 case ProvisioningCallback.OSU_FAILURE_OSU_PROVIDER_NOT_FOUND: 8466 provisionFailureCode = PasspointProvisionStats 8467 .OSU_FAILURE_OSU_PROVIDER_NOT_FOUND; 8468 break; 8469 default: 8470 provisionFailureCode = PasspointProvisionStats.OSU_FAILURE_UNKNOWN; 8471 } 8472 mPasspointProvisionFailureCounts.increment(provisionFailureCode); 8473 } 8474 } 8475 8476 /** 8477 * Add to the histogram of number of BSSIDs filtered out from network selection. 8478 */ 8479 public void incrementNetworkSelectionFilteredBssidCount(int numBssid) { 8480 mBssidBlocklistStats.networkSelectionFilteredBssidCount.increment(numBssid); 8481 } 8482 8483 /** 8484 * Increment the number of network connections skipped due to the high movement feature. 8485 */ 8486 public void incrementNumHighMovementConnectionSkipped() { 8487 mBssidBlocklistStats.numHighMovementConnectionSkipped++; 8488 } 8489 8490 /** 8491 * Increment the number of network connections initiated while under the high movement 8492 * feature. 8493 */ 8494 public void incrementNumHighMovementConnectionStarted() { 8495 mBssidBlocklistStats.numHighMovementConnectionStarted++; 8496 } 8497 8498 /** 8499 * Increment the number of times BSSIDs are blocked per reason. 8500 * @param blockReason one of {@link WifiBlocklistMonitor.FailureReason} 8501 */ 8502 public void incrementBssidBlocklistCount(int blockReason) { 8503 mBssidBlocklistStats.incrementBssidBlocklistCount(blockReason); 8504 } 8505 8506 /** 8507 * Increment the number of times WifiConfigurations are blocked per reason. 8508 * @param blockReason one of {@Link NetworkSelectionStatus.NetworkSelectionDisableReason} 8509 */ 8510 public void incrementWificonfigurationBlocklistCount(int blockReason) { 8511 mBssidBlocklistStats.incrementWificonfigurationBlocklistCount(blockReason); 8512 } 8513 8514 /** 8515 * Increment number of passpoint provision success 8516 */ 8517 public void incrementPasspointProvisionSuccess() { 8518 synchronized (mLock) { 8519 mNumProvisionSuccess++; 8520 } 8521 } 8522 8523 /** 8524 * Increment number of IP renewal failures. 8525 */ 8526 public void incrementIpRenewalFailure() { 8527 synchronized (mLock) { 8528 mWifiLogProto.numIpRenewalFailure++; 8529 } 8530 } 8531 8532 /** 8533 * Sets the duration for evaluating Wifi condition to trigger a data stall 8534 */ 8535 public void setDataStallDurationMs(int duration) { 8536 synchronized (mLock) { 8537 mExperimentValues.dataStallDurationMs = duration; 8538 } 8539 } 8540 8541 /** 8542 * Sets the threshold of Tx throughput below which to trigger a data stall 8543 */ 8544 public void setDataStallTxTputThrKbps(int txTputThr) { 8545 synchronized (mLock) { 8546 mExperimentValues.dataStallTxTputThrKbps = txTputThr; 8547 } 8548 } 8549 8550 /** 8551 * Sets the threshold of Rx throughput below which to trigger a data stall 8552 */ 8553 public void setDataStallRxTputThrKbps(int rxTputThr) { 8554 synchronized (mLock) { 8555 mExperimentValues.dataStallRxTputThrKbps = rxTputThr; 8556 } 8557 } 8558 8559 /** 8560 * Sets the threshold of Tx packet error rate above which to trigger a data stall 8561 */ 8562 public void setDataStallTxPerThr(int txPerThr) { 8563 synchronized (mLock) { 8564 mExperimentValues.dataStallTxPerThr = txPerThr; 8565 } 8566 } 8567 8568 /** 8569 * Sets the threshold of CCA level above which to trigger a data stall 8570 */ 8571 public void setDataStallCcaLevelThr(int ccaLevel) { 8572 synchronized (mLock) { 8573 mExperimentValues.dataStallCcaLevelThr = ccaLevel; 8574 } 8575 } 8576 8577 /** 8578 * Sets health monitor RSSI poll valid time in ms 8579 */ 8580 public void setHealthMonitorRssiPollValidTimeMs(int rssiPollValidTimeMs) { 8581 synchronized (mLock) { 8582 mExperimentValues.healthMonitorRssiPollValidTimeMs = rssiPollValidTimeMs; 8583 } 8584 } 8585 8586 /** 8587 * Increment connection duration while link layer stats report are on 8588 */ 8589 public void incrementConnectionDuration(String ifaceName, int timeDeltaLastTwoPollsMs, 8590 boolean isThroughputSufficient, boolean isCellularDataAvailable, int rssi, int txKbps, 8591 int rxKbps) { 8592 synchronized (mLock) { 8593 if (!isPrimary(ifaceName)) { 8594 return; 8595 } 8596 mConnectionDurationStats.incrementDurationCount(timeDeltaLastTwoPollsMs, 8597 isThroughputSufficient, isCellularDataAvailable, mWifiWins); 8598 WifiUsabilityState wifiUsabilityState = mWifiUsabilityStatePerIface.getOrDefault( 8599 ifaceName, WifiUsabilityState.UNKNOWN); 8600 int band = KnownBandsChannelHelper.getBand(mLastPollFreq); 8601 WifiStatsLog.write(WifiStatsLog.WIFI_HEALTH_STAT_REPORTED, timeDeltaLastTwoPollsMs, 8602 isThroughputSufficient || !mWifiWins, isCellularDataAvailable, band, rssi, 8603 txKbps, rxKbps, mScorerUid, (wifiUsabilityState == WifiUsabilityState.USABLE), 8604 convertWifiUsabilityState(wifiUsabilityState)); 8605 } 8606 } 8607 8608 /** 8609 * Sets the status to indicate whether external WiFi connected network scorer is present or not. 8610 */ 8611 public void setIsExternalWifiScorerOn(boolean value, int callerUid) { 8612 synchronized (mLock) { 8613 mWifiLogProto.isExternalWifiScorerOn = value; 8614 mScorerUid = callerUid; 8615 } 8616 } 8617 8618 /** 8619 * Note Wi-Fi off metrics 8620 */ 8621 public void noteWifiOff(boolean isDeferred, boolean isTimeout, int duration) { 8622 synchronized (mLock) { 8623 mWifiOffMetrics.numWifiOff++; 8624 if (isDeferred) { 8625 mWifiOffMetrics.numWifiOffDeferring++; 8626 if (isTimeout) { 8627 mWifiOffMetrics.numWifiOffDeferringTimeout++; 8628 } 8629 mWifiOffMetrics.wifiOffDeferringTimeHistogram.increment(duration); 8630 } 8631 } 8632 } 8633 8634 /** 8635 * Increment number of BSSIDs filtered out from network selection due to MBO Association 8636 * disallowed indication. 8637 */ 8638 public void incrementNetworkSelectionFilteredBssidCountDueToMboAssocDisallowInd() { 8639 synchronized (mLock) { 8640 mWifiLogProto.numBssidFilteredDueToMboAssocDisallowInd++; 8641 } 8642 } 8643 8644 /** 8645 * Increment number of times BSS transition management request frame is received from the AP. 8646 */ 8647 public void incrementSteeringRequestCount() { 8648 synchronized (mLock) { 8649 mWifiLogProto.numSteeringRequest++; 8650 } 8651 } 8652 8653 /** 8654 * Increment number of times force scan is triggered due to a 8655 * BSS transition management request frame from AP. 8656 */ 8657 public void incrementForceScanCountDueToSteeringRequest() { 8658 synchronized (mLock) { 8659 mWifiLogProto.numForceScanDueToSteeringRequest++; 8660 } 8661 } 8662 8663 /** 8664 * Increment number of times STA received cellular switch 8665 * request from MBO supported AP. 8666 */ 8667 public void incrementMboCellularSwitchRequestCount() { 8668 synchronized (mLock) { 8669 mWifiLogProto.numMboCellularSwitchRequest++; 8670 } 8671 } 8672 8673 /** 8674 * Increment number of times STA received steering request 8675 * including MBO association retry delay. 8676 */ 8677 public void incrementSteeringRequestCountIncludingMboAssocRetryDelay() { 8678 synchronized (mLock) { 8679 mWifiLogProto.numSteeringRequestIncludingMboAssocRetryDelay++; 8680 } 8681 } 8682 8683 /** 8684 * Increment number of connect request to AP adding FILS AKM. 8685 */ 8686 public void incrementConnectRequestWithFilsAkmCount() { 8687 synchronized (mLock) { 8688 mWifiLogProto.numConnectRequestWithFilsAkm++; 8689 } 8690 } 8691 8692 /** 8693 * Increment number of times STA connected through FILS 8694 * authentication. 8695 */ 8696 public void incrementL2ConnectionThroughFilsAuthCount() { 8697 synchronized (mLock) { 8698 mWifiLogProto.numL2ConnectionThroughFilsAuthentication++; 8699 } 8700 } 8701 8702 /** 8703 * Note SoftapConfig Reset Metrics 8704 */ 8705 public void noteSoftApConfigReset(SoftApConfiguration originalConfig, 8706 SoftApConfiguration newConfig) { 8707 synchronized (mLock) { 8708 if (originalConfig.getSecurityType() != newConfig.getSecurityType()) { 8709 mSoftApConfigLimitationMetrics.numSecurityTypeResetToDefault++; 8710 } 8711 if (originalConfig.getMaxNumberOfClients() != newConfig.getMaxNumberOfClients()) { 8712 mSoftApConfigLimitationMetrics.numMaxClientSettingResetToDefault++; 8713 } 8714 if (originalConfig.isClientControlByUserEnabled() 8715 != newConfig.isClientControlByUserEnabled()) { 8716 mSoftApConfigLimitationMetrics.numClientControlByUserResetToDefault++; 8717 } 8718 } 8719 } 8720 8721 /** 8722 * Note Softap client blocked due to max client limitation 8723 */ 8724 public void noteSoftApClientBlocked(int maxClient) { 8725 mSoftApConfigLimitationMetrics.maxClientSettingWhenReachHistogram.increment(maxClient); 8726 } 8727 8728 /** 8729 * Increment number of connection with different BSSID between framework and firmware selection. 8730 */ 8731 public void incrementNumBssidDifferentSelectionBetweenFrameworkAndFirmware() { 8732 synchronized (mLock) { 8733 mWifiLogProto.numBssidDifferentSelectionBetweenFrameworkAndFirmware++; 8734 } 8735 } 8736 8737 /** 8738 * Note the carrier wifi network connected successfully. 8739 */ 8740 public void incrementNumOfCarrierWifiConnectionSuccess() { 8741 synchronized (mLock) { 8742 mCarrierWifiMetrics.numConnectionSuccess++; 8743 } 8744 } 8745 8746 /** 8747 * Note the carrier wifi network connection authentication failure. 8748 */ 8749 public void incrementNumOfCarrierWifiConnectionAuthFailure() { 8750 synchronized (mLock) { 8751 mCarrierWifiMetrics.numConnectionAuthFailure++; 8752 } 8753 } 8754 8755 /** 8756 * Note the carrier wifi network connection non-authentication failure. 8757 */ 8758 public void incrementNumOfCarrierWifiConnectionNonAuthFailure() { 8759 synchronized (mLock) { 8760 mCarrierWifiMetrics.numConnectionNonAuthFailure++; 8761 } 8762 } 8763 8764 /** 8765 * Set Adaptive Connectivity state (On/Off) 8766 */ 8767 public void setAdaptiveConnectivityState(boolean adaptiveConnectivityEnabled) { 8768 synchronized (mLock) { 8769 mAdaptiveConnectivityEnabled = adaptiveConnectivityEnabled; 8770 } 8771 } 8772 8773 /** 8774 * Get total beacon receive count 8775 */ 8776 public long getTotalBeaconRxCount() { 8777 return mLastTotalBeaconRx; 8778 } 8779 8780 /** Get total beacon receive count for the link */ 8781 public long getTotalBeaconRxCount(int linkId) { 8782 if (!mLastLinkMetrics.contains(linkId)) return 0; 8783 return mLastLinkMetrics.get(linkId).getTotalBeaconRx(); 8784 } 8785 8786 /** Get link usage state */ 8787 public @android.net.wifi.WifiUsabilityStatsEntry.LinkState int getLinkUsageState(int linkId) { 8788 if (!mLastLinkMetrics.contains(linkId)) { 8789 return android.net.wifi.WifiUsabilityStatsEntry.LINK_STATE_UNKNOWN; 8790 } 8791 return mLastLinkMetrics.get(linkId).getLinkUsageState(); 8792 } 8793 8794 /** Note whether Wifi was enabled at boot time. */ 8795 public void noteWifiEnabledDuringBoot(boolean isWifiEnabled) { 8796 synchronized (mLock) { 8797 if (mIsFirstConnectionAttemptComplete 8798 || mFirstConnectAfterBootStats == null 8799 || mFirstConnectAfterBootStats.wifiEnabledAtBoot != null) { 8800 return; 8801 } 8802 Attempt wifiEnabledAtBoot = new Attempt(); 8803 wifiEnabledAtBoot.isSuccess = isWifiEnabled; 8804 wifiEnabledAtBoot.timestampSinceBootMillis = mClock.getElapsedSinceBootMillis(); 8805 mFirstConnectAfterBootStats.wifiEnabledAtBoot = wifiEnabledAtBoot; 8806 if (!isWifiEnabled) { 8807 mIsFirstConnectionAttemptComplete = true; 8808 } 8809 } 8810 } 8811 8812 /** Note the first network selection after boot. */ 8813 public void noteFirstNetworkSelectionAfterBoot(boolean wasAnyCandidatesFound) { 8814 synchronized (mLock) { 8815 if (mIsFirstConnectionAttemptComplete 8816 || mFirstConnectAfterBootStats == null 8817 || mFirstConnectAfterBootStats.firstNetworkSelection != null) { 8818 return; 8819 } 8820 Attempt firstNetworkSelection = new Attempt(); 8821 firstNetworkSelection.isSuccess = wasAnyCandidatesFound; 8822 firstNetworkSelection.timestampSinceBootMillis = mClock.getElapsedSinceBootMillis(); 8823 mFirstConnectAfterBootStats.firstNetworkSelection = firstNetworkSelection; 8824 if (!wasAnyCandidatesFound) { 8825 mIsFirstConnectionAttemptComplete = true; 8826 } 8827 } 8828 } 8829 8830 /** Note the first L2 connection after boot. */ 8831 public void noteFirstL2ConnectionAfterBoot(boolean wasConnectionSuccessful) { 8832 synchronized (mLock) { 8833 if (mIsFirstConnectionAttemptComplete 8834 || mFirstConnectAfterBootStats == null 8835 || mFirstConnectAfterBootStats.firstL2Connection != null) { 8836 return; 8837 } 8838 Attempt firstL2Connection = new Attempt(); 8839 firstL2Connection.isSuccess = wasConnectionSuccessful; 8840 firstL2Connection.timestampSinceBootMillis = mClock.getElapsedSinceBootMillis(); 8841 mFirstConnectAfterBootStats.firstL2Connection = firstL2Connection; 8842 if (!wasConnectionSuccessful) { 8843 mIsFirstConnectionAttemptComplete = true; 8844 } 8845 } 8846 } 8847 8848 /** Note the first L3 connection after boot. */ 8849 public void noteFirstL3ConnectionAfterBoot(boolean wasConnectionSuccessful) { 8850 synchronized (mLock) { 8851 if (mIsFirstConnectionAttemptComplete 8852 || mFirstConnectAfterBootStats == null 8853 || mFirstConnectAfterBootStats.firstL3Connection != null) { 8854 return; 8855 } 8856 Attempt firstL3Connection = new Attempt(); 8857 firstL3Connection.isSuccess = wasConnectionSuccessful; 8858 firstL3Connection.timestampSinceBootMillis = mClock.getElapsedSinceBootMillis(); 8859 mFirstConnectAfterBootStats.firstL3Connection = firstL3Connection; 8860 if (!wasConnectionSuccessful) { 8861 mIsFirstConnectionAttemptComplete = true; 8862 } 8863 } 8864 } 8865 8866 private static String attemptToString(@Nullable Attempt attempt) { 8867 if (attempt == null) return "Attempt=null"; 8868 return "Attempt{" 8869 + "timestampSinceBootMillis=" + attempt.timestampSinceBootMillis 8870 + ",isSuccess=" + attempt.isSuccess 8871 + "}"; 8872 } 8873 8874 private static String firstConnectAfterBootStatsToString( 8875 @Nullable FirstConnectAfterBootStats stats) { 8876 if (stats == null) return "FirstConnectAfterBootStats=null"; 8877 return "FirstConnectAfterBootStats{" 8878 + "wifiEnabledAtBoot=" + attemptToString(stats.wifiEnabledAtBoot) 8879 + ",firstNetworkSelection" + attemptToString(stats.firstNetworkSelection) 8880 + ",firstL2Connection" + attemptToString(stats.firstL2Connection) 8881 + ",firstL3Connection" + attemptToString(stats.firstL3Connection) 8882 + "}"; 8883 } 8884 8885 public ScanMetrics getScanMetrics() { 8886 return mScanMetrics; 8887 } 8888 8889 public enum ScanType { SINGLE, BACKGROUND } 8890 8891 public enum PnoScanState { STARTED, FAILED_TO_START, COMPLETED_NETWORK_FOUND, FAILED } 8892 8893 /** 8894 * This class reports Scan metrics to statsd and holds intermediate scan request state. 8895 */ 8896 public static class ScanMetrics { 8897 private static final String TAG_SCANS = "ScanMetrics"; 8898 private static final String GMS_PACKAGE = "com.google.android.gms"; 8899 8900 // Scan types. 8901 public static final int SCAN_TYPE_SINGLE = 0; 8902 public static final int SCAN_TYPE_BACKGROUND = 1; 8903 public static final int SCAN_TYPE_MAX_VALUE = SCAN_TYPE_BACKGROUND; 8904 @IntDef(prefix = { "SCAN_TYPE_" }, value = { 8905 SCAN_TYPE_SINGLE, 8906 SCAN_TYPE_BACKGROUND, 8907 }) 8908 public @interface ScanType {} 8909 8910 // PNO scan states. 8911 public static final int PNO_SCAN_STATE_STARTED = 1; 8912 public static final int PNO_SCAN_STATE_FAILED_TO_START = 2; 8913 public static final int PNO_SCAN_STATE_COMPLETED_NETWORK_FOUND = 3; 8914 public static final int PNO_SCAN_STATE_FAILED = 4; 8915 @IntDef(prefix = { "PNO_SCAN_STATE_" }, value = { 8916 PNO_SCAN_STATE_STARTED, 8917 PNO_SCAN_STATE_FAILED_TO_START, 8918 PNO_SCAN_STATE_COMPLETED_NETWORK_FOUND, 8919 PNO_SCAN_STATE_FAILED 8920 }) 8921 public @interface PnoScanState {} 8922 8923 private final Object mLock = new Object(); 8924 private Clock mClock; 8925 8926 private List<String> mSettingsPackages = new ArrayList<>(); 8927 private int mGmsUid = -1; 8928 8929 // mNextScanState collects metadata about the next scan that's about to happen. 8930 // It is mutated by external callers via setX methods before the call to logScanStarted. 8931 private State mNextScanState = new State(); 8932 // mActiveScanState is an immutable copy of mNextScanState during the scan process, 8933 // i.e. between logScanStarted and logScanSucceeded/Failed. Since the state is pushed to 8934 // statsd only when a scan ends, it's important to keep the immutable copy 8935 // for the duration of the scan. 8936 private State[] mActiveScanStates = new State[SCAN_TYPE_MAX_VALUE + 1]; 8937 8938 ScanMetrics(Context context, Clock clock) { 8939 mClock = clock; 8940 8941 PackageManager pm = context.getPackageManager(); 8942 if (pm != null) { 8943 Intent settingsIntent = new Intent(Settings.ACTION_SETTINGS); 8944 List<ResolveInfo> packages = pm.queryIntentActivities(settingsIntent, 0); 8945 for (ResolveInfo res : packages) { 8946 String packageName = res.activityInfo.packageName; 8947 Log.d(TAG_SCANS, "Settings package: " + packageName); 8948 mSettingsPackages.add(packageName); 8949 } 8950 } 8951 8952 try { 8953 mGmsUid = context.getPackageManager().getApplicationInfo(GMS_PACKAGE, 0).uid; 8954 Log.d(TAG_SCANS, "GMS uid: " + mGmsUid); 8955 } catch (Exception e) { 8956 Log.e(TAG_SCANS, "Can't get GMS uid"); 8957 } 8958 } 8959 8960 /** 8961 * Set WorkSource for the upcoming scan request. 8962 * 8963 * @param workSource 8964 */ 8965 public void setWorkSource(WorkSource workSource) { 8966 synchronized (mLock) { 8967 if (mNextScanState.mWorkSource == null) { 8968 mNextScanState.mWorkSource = workSource; 8969 if (DBG) Log.d(TAG_SCANS, "setWorkSource: workSource = " + workSource); 8970 } 8971 } 8972 } 8973 8974 /** 8975 * Set ClientUid for the upcoming scan request. 8976 * 8977 * @param uid 8978 */ 8979 public void setClientUid(int uid) { 8980 synchronized (mLock) { 8981 mNextScanState.mClientUid = uid; 8982 8983 if (DBG) Log.d(TAG_SCANS, "setClientUid: uid = " + uid); 8984 } 8985 } 8986 8987 /** 8988 * Set Importance for the upcoming scan request. 8989 * 8990 * @param packageImportance See {@link ActivityManager.RunningAppProcessInfo.Importance} 8991 */ 8992 public void setImportance(int packageImportance) { 8993 synchronized (mLock) { 8994 mNextScanState.mPackageImportance = packageImportance; 8995 8996 if (DBG) { 8997 Log.d(TAG_SCANS, 8998 "setRequestFromBackground: packageImportance = " + packageImportance); 8999 } 9000 } 9001 } 9002 9003 /** 9004 * Indicate that a scan started. 9005 * @param scanType See {@link ScanMetrics.ScanType} 9006 */ 9007 public void logScanStarted(@ScanType int scanType) { 9008 synchronized (mLock) { 9009 if (DBG) Log.d(TAG_SCANS, "logScanStarted"); 9010 9011 mNextScanState.mTimeStartMillis = mClock.getElapsedSinceBootMillis(); 9012 mActiveScanStates[scanType] = mNextScanState; 9013 mNextScanState = new State(); 9014 } 9015 } 9016 9017 /** 9018 * Indicate that a scan failed to start. 9019 * @param scanType See {@link ScanMetrics.ScanType} 9020 */ 9021 public void logScanFailedToStart(@ScanType int scanType) { 9022 synchronized (mLock) { 9023 Log.d(TAG_SCANS, "logScanFailedToStart"); 9024 9025 mNextScanState.mTimeStartMillis = mClock.getElapsedSinceBootMillis(); 9026 mActiveScanStates[scanType] = mNextScanState; 9027 mNextScanState = new State(); 9028 9029 log(scanType, WifiStatsLog.WIFI_SCAN_REPORTED__RESULT__RESULT_FAILED_TO_START, 0); 9030 mActiveScanStates[scanType] = null; 9031 } 9032 } 9033 9034 /** 9035 * Indicate that a scan finished successfully. 9036 * @param scanType See {@link ScanMetrics.ScanType} 9037 * @param countOfNetworksFound How many networks were found. 9038 */ 9039 public void logScanSucceeded(@ScanType int scanType, int countOfNetworksFound) { 9040 synchronized (mLock) { 9041 if (DBG) Log.d(TAG_SCANS, "logScanSucceeded: found = " + countOfNetworksFound); 9042 9043 log(scanType, WifiStatsLog.WIFI_SCAN_REPORTED__RESULT__RESULT_SUCCESS, 9044 countOfNetworksFound); 9045 mActiveScanStates[scanType] = null; 9046 } 9047 } 9048 9049 /** 9050 * Log a PNO scan event: start/finish/fail. 9051 * @param pnoScanState See {@link PnoScanState} 9052 */ 9053 public void logPnoScanEvent(@PnoScanState int pnoScanState) { 9054 synchronized (mLock) { 9055 int state = 0; 9056 9057 switch (pnoScanState) { 9058 case PNO_SCAN_STATE_STARTED: 9059 state = WifiStatsLog.WIFI_PNO_SCAN_REPORTED__STATE__STARTED; 9060 break; 9061 case PNO_SCAN_STATE_FAILED_TO_START: 9062 state = WifiStatsLog.WIFI_PNO_SCAN_REPORTED__STATE__FAILED_TO_START; 9063 break; 9064 case PNO_SCAN_STATE_COMPLETED_NETWORK_FOUND: 9065 state = WifiStatsLog.WIFI_PNO_SCAN_REPORTED__STATE__FINISHED_NETWORKS_FOUND; 9066 break; 9067 case PNO_SCAN_STATE_FAILED: 9068 state = WifiStatsLog.WIFI_PNO_SCAN_REPORTED__STATE__FAILED; 9069 break; 9070 } 9071 9072 WifiStatsLog.write(WifiStatsLog.WIFI_PNO_SCAN_REPORTED, state); 9073 9074 if (DBG) Log.d(TAG_SCANS, "logPnoScanEvent: pnoScanState = " + pnoScanState); 9075 } 9076 } 9077 9078 /** 9079 * Indicate that a scan failed. 9080 */ 9081 public void logScanFailed(@ScanType int scanType) { 9082 synchronized (mLock) { 9083 if (DBG) Log.d(TAG_SCANS, "logScanFailed"); 9084 9085 log(scanType, WifiStatsLog.WIFI_SCAN_REPORTED__RESULT__RESULT_FAILED_TO_SCAN, 0); 9086 mActiveScanStates[scanType] = null; 9087 } 9088 } 9089 9090 private void log(@ScanType int scanType, int result, int countNetworks) { 9091 State state = mActiveScanStates[scanType]; 9092 9093 if (state == null) { 9094 if (DBG) Log.e(TAG_SCANS, "Wifi scan result log called with no prior start calls!"); 9095 return; 9096 } 9097 9098 int type = WifiStatsLog.WIFI_SCAN_REPORTED__TYPE__TYPE_UNKNOWN; 9099 if (scanType == SCAN_TYPE_SINGLE) { 9100 type = WifiStatsLog.WIFI_SCAN_REPORTED__TYPE__TYPE_SINGLE; 9101 } else if (scanType == SCAN_TYPE_BACKGROUND) { 9102 type = WifiStatsLog.WIFI_SCAN_REPORTED__TYPE__TYPE_BACKGROUND; 9103 } 9104 9105 long duration = mClock.getElapsedSinceBootMillis() - state.mTimeStartMillis; 9106 9107 int source = WifiStatsLog.WIFI_SCAN_REPORTED__SOURCE__SOURCE_NO_WORK_SOURCE; 9108 if (state.mClientUid != -1 && state.mClientUid == mGmsUid) { 9109 source = WifiStatsLog.WIFI_SCAN_REPORTED__SOURCE__SOURCE_GMS; 9110 } else if (state.mWorkSource != null) { 9111 if (state.mWorkSource.equals(ClientModeImpl.WIFI_WORK_SOURCE)) { 9112 source = WifiStatsLog.WIFI_SCAN_REPORTED__SOURCE__SOURCE_WIFI_STACK; 9113 } else { 9114 source = WifiStatsLog.WIFI_SCAN_REPORTED__SOURCE__SOURCE_OTHER_APP; 9115 9116 for (int i = 0; i < state.mWorkSource.size(); i++) { 9117 if (mSettingsPackages.contains( 9118 state.mWorkSource.getPackageName(i))) { 9119 source = WifiStatsLog.WIFI_SCAN_REPORTED__SOURCE__SOURCE_SETTINGS_APP; 9120 break; 9121 } 9122 } 9123 } 9124 } 9125 9126 int importance = WifiStatsLog.WIFI_SCAN_REPORTED__IMPORTANCE__IMPORTANCE_UNKNOWN; 9127 if (state.mPackageImportance != -1) { 9128 if (state.mPackageImportance 9129 <= ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) { 9130 importance = WifiStatsLog.WIFI_SCAN_REPORTED__IMPORTANCE__IMPORTANCE_FOREGROUND; 9131 } else if (state.mPackageImportance 9132 <= ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND_SERVICE) { 9133 importance = 9134 WifiStatsLog.WIFI_SCAN_REPORTED__IMPORTANCE__IMPORTANCE_FOREGROUND_SERVICE; 9135 } else { 9136 importance = WifiStatsLog.WIFI_SCAN_REPORTED__IMPORTANCE__IMPORTANCE_BACKGROUND; 9137 } 9138 } 9139 9140 WifiStatsLog.write(WifiStatsLog.WIFI_SCAN_REPORTED, 9141 type, 9142 result, 9143 source, 9144 importance, 9145 (int) duration, 9146 countNetworks); 9147 9148 if (DBG) { 9149 Log.d(TAG_SCANS, 9150 "WifiScanReported: type = " + type 9151 + ", result = " + result 9152 + ", source = " + source 9153 + ", importance = " + importance 9154 + ", networks = " + countNetworks); 9155 } 9156 } 9157 9158 static class State { 9159 WorkSource mWorkSource = null; 9160 int mClientUid = -1; 9161 // see @ActivityManager.RunningAppProcessInfo.Importance 9162 int mPackageImportance = -1; 9163 9164 long mTimeStartMillis; 9165 } 9166 } 9167 9168 /** Set whether Make Before Break is supported by the hardware and enabled. */ 9169 public void setIsMakeBeforeBreakSupported(boolean supported) { 9170 synchronized (mLock) { 9171 mWifiToWifiSwitchStats.isMakeBeforeBreakSupported = supported; 9172 } 9173 } 9174 9175 /** 9176 * Increment the number of times Wifi to Wifi switch was triggered. This includes Make Before 9177 * Break and Break Before Make. 9178 */ 9179 public void incrementWifiToWifiSwitchTriggerCount() { 9180 synchronized (mLock) { 9181 mWifiToWifiSwitchStats.wifiToWifiSwitchTriggerCount++; 9182 } 9183 } 9184 9185 /** 9186 * Increment the Number of times Wifi to Wifi switch was triggered using Make Before Break 9187 * (MBB). Note that MBB may not always be used for various reasons e.g. no additional iface 9188 * available due to ongoing SoftAP, both old and new network have MAC randomization disabled, 9189 * etc. 9190 */ 9191 public void incrementMakeBeforeBreakTriggerCount() { 9192 synchronized (mLock) { 9193 mWifiToWifiSwitchStats.makeBeforeBreakTriggerCount++; 9194 } 9195 } 9196 9197 /** 9198 * Increment the number of times Make Before Break was aborted due to the new network not having 9199 * internet. 9200 */ 9201 public void incrementMakeBeforeBreakNoInternetCount() { 9202 synchronized (mLock) { 9203 mWifiToWifiSwitchStats.makeBeforeBreakNoInternetCount++; 9204 } 9205 } 9206 9207 /** 9208 * Increment the number of times where, for some reason, Make Before Break resulted in the 9209 * loss of the primary ClientModeManager, and we needed to recover by making one of the 9210 * SECONDARY_TRANSIENT ClientModeManagers primary. 9211 */ 9212 public void incrementMakeBeforeBreakRecoverPrimaryCount() { 9213 synchronized (mLock) { 9214 mWifiToWifiSwitchStats.makeBeforeBreakRecoverPrimaryCount++; 9215 } 9216 } 9217 9218 /** 9219 * Increment the number of times the new network in Make Before Break had its internet 9220 * connection validated. 9221 */ 9222 public void incrementMakeBeforeBreakInternetValidatedCount() { 9223 synchronized (mLock) { 9224 mWifiToWifiSwitchStats.makeBeforeBreakInternetValidatedCount++; 9225 } 9226 } 9227 9228 /** 9229 * Increment the number of times the old network in Make Before Break was successfully 9230 * transitioned from PRIMARY to SECONDARY_TRANSIENT role. 9231 */ 9232 public void incrementMakeBeforeBreakSuccessCount() { 9233 synchronized (mLock) { 9234 mWifiToWifiSwitchStats.makeBeforeBreakSuccessCount++; 9235 } 9236 } 9237 9238 /** 9239 * Increment the number of times the old network in Make Before Break completed lingering and 9240 * was disconnected. 9241 * @param duration the lingering duration in ms 9242 */ 9243 public void incrementMakeBeforeBreakLingerCompletedCount(long duration) { 9244 synchronized (mLock) { 9245 mWifiToWifiSwitchStats.makeBeforeBreakLingerCompletedCount++; 9246 int lingeringDurationSeconds = Math.min(MBB_LINGERING_DURATION_MAX_SECONDS, 9247 (int) duration / 1000); 9248 mMakeBeforeBreakLingeringDurationSeconds.increment(lingeringDurationSeconds); 9249 } 9250 } 9251 9252 private String wifiToWifiSwitchStatsToString(WifiToWifiSwitchStats stats) { 9253 return "WifiToWifiSwitchStats{" 9254 + "isMakeBeforeBreakSupported=" + stats.isMakeBeforeBreakSupported 9255 + ",wifiToWifiSwitchTriggerCount=" + stats.wifiToWifiSwitchTriggerCount 9256 + ",makeBeforeBreakTriggerCount=" + stats.makeBeforeBreakTriggerCount 9257 + ",makeBeforeBreakNoInternetCount=" + stats.makeBeforeBreakNoInternetCount 9258 + ",makeBeforeBreakRecoverPrimaryCount=" + stats.makeBeforeBreakRecoverPrimaryCount 9259 + ",makeBeforeBreakInternetValidatedCount=" 9260 + stats.makeBeforeBreakInternetValidatedCount 9261 + ",makeBeforeBreakSuccessCount=" + stats.makeBeforeBreakSuccessCount 9262 + ",makeBeforeBreakLingerCompletedCount=" 9263 + stats.makeBeforeBreakLingerCompletedCount 9264 + ",makeBeforeBreakLingeringDurationSeconds=" 9265 + mMakeBeforeBreakLingeringDurationSeconds 9266 + "}"; 9267 } 9268 9269 /** 9270 * Increment number of number of Passpoint connections with a venue URL 9271 */ 9272 public void incrementTotalNumberOfPasspointConnectionsWithVenueUrl() { 9273 synchronized (mLock) { 9274 mWifiLogProto.totalNumberOfPasspointConnectionsWithVenueUrl++; 9275 } 9276 } 9277 9278 /** 9279 * Increment number of number of Passpoint connections with a T&C URL 9280 */ 9281 public void incrementTotalNumberOfPasspointConnectionsWithTermsAndConditionsUrl() { 9282 synchronized (mLock) { 9283 mWifiLogProto.totalNumberOfPasspointConnectionsWithTermsAndConditionsUrl++; 9284 } 9285 } 9286 9287 /** 9288 * Increment number of successful acceptance of Passpoint T&C 9289 */ 9290 public void incrementTotalNumberOfPasspointAcceptanceOfTermsAndConditions() { 9291 synchronized (mLock) { 9292 mWifiLogProto.totalNumberOfPasspointAcceptanceOfTermsAndConditions++; 9293 } 9294 } 9295 9296 /** 9297 * Increment number of Passpoint profiles with decorated identity prefix 9298 */ 9299 public void incrementTotalNumberOfPasspointProfilesWithDecoratedIdentity() { 9300 synchronized (mLock) { 9301 mWifiLogProto.totalNumberOfPasspointProfilesWithDecoratedIdentity++; 9302 } 9303 } 9304 9305 /** 9306 * Increment number of Passpoint Deauth-Imminent notification scope 9307 */ 9308 public void incrementPasspointDeauthImminentScope(boolean isEss) { 9309 synchronized (mLock) { 9310 mPasspointDeauthImminentScope.increment(isEss ? PASSPOINT_DEAUTH_IMMINENT_SCOPE_ESS 9311 : PASSPOINT_DEAUTH_IMMINENT_SCOPE_BSS); 9312 } 9313 } 9314 9315 /** 9316 * Increment number of times connection failure status reported per 9317 * WifiConfiguration.RecentFailureReason 9318 */ 9319 public void incrementRecentFailureAssociationStatusCount( 9320 @WifiConfiguration.RecentFailureReason int reason) { 9321 synchronized (mLock) { 9322 mRecentFailureAssociationStatus.increment(reason); 9323 } 9324 } 9325 9326 /** 9327 * Logging the time it takes for save config to the storage. 9328 * @param time the time it take to write to the storage 9329 */ 9330 public void wifiConfigStored(int time) { 9331 WifiStatsLog.write(WIFI_CONFIG_SAVED, time); 9332 } 9333 9334 /** 9335 * Set Wi-Fi usability state per interface as predicted by the scorer 9336 */ 9337 public void setScorerPredictedWifiUsabilityState(String ifaceName, 9338 WifiUsabilityState usabilityState) { 9339 mWifiUsabilityStatePerIface.put(ifaceName, usabilityState); 9340 } 9341 9342 private static int getSoftApStartedStartResult(@SoftApManager.StartResult int startResult) { 9343 switch (startResult) { 9344 case SoftApManager.START_RESULT_UNKNOWN: 9345 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_UNKNOWN; 9346 case SoftApManager.START_RESULT_SUCCESS: 9347 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_SUCCESS; 9348 case SoftApManager.START_RESULT_FAILURE_GENERAL: 9349 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_GENERAL; 9350 9351 case SoftApManager.START_RESULT_FAILURE_NO_CHANNEL: 9352 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_NO_CHANNEL; 9353 case SoftApManager.START_RESULT_FAILURE_UNSUPPORTED_CONFIG: 9354 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_UNSUPPORTED_CONFIG; 9355 case SoftApManager.START_RESULT_FAILURE_START_HAL: 9356 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_START_HAL; 9357 case SoftApManager.START_RESULT_FAILURE_START_HOSTAPD: 9358 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_START_HOSTAPD; 9359 case SoftApManager.START_RESULT_FAILURE_INTERFACE_CONFLICT_USER_REJECTED: 9360 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_INTERFACE_CONFLICT_USER_REJECTED; 9361 case SoftApManager.START_RESULT_FAILURE_INTERFACE_CONFLICT: 9362 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_INTERFACE_CONFLICT; 9363 case SoftApManager.START_RESULT_FAILURE_CREATE_INTERFACE: 9364 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_CREATE_INTERFACE; 9365 case SoftApManager.START_RESULT_FAILURE_SET_COUNTRY_CODE: 9366 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_SET_COUNTRY_CODE; 9367 case SoftApManager.START_RESULT_FAILURE_SET_MAC_ADDRESS: 9368 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_SET_MAC_ADDRESS; 9369 case SoftApManager.START_RESULT_FAILURE_REGISTER_AP_CALLBACK_HOSTAPD: 9370 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_REGISTER_AP_CALLBACK_HOSTAPD; 9371 case SoftApManager.START_RESULT_FAILURE_REGISTER_AP_CALLBACK_WIFICOND: 9372 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_REGISTER_AP_CALLBACK_WIFICOND; 9373 case SoftApManager.START_RESULT_FAILURE_ADD_AP_HOSTAPD: 9374 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_FAILURE_ADD_AP_HOSTAPD; 9375 default: 9376 Log.wtf(TAG, "getSoftApStartedStartResult: unknown StartResult" + startResult); 9377 return WifiStatsLog.SOFT_AP_STARTED__RESULT__START_RESULT_UNKNOWN; 9378 } 9379 } 9380 9381 private static int getSoftApStartedRole(ActiveModeManager.SoftApRole role) { 9382 if (ActiveModeManager.ROLE_SOFTAP_LOCAL_ONLY.equals(role)) { 9383 return WifiStatsLog.SOFT_AP_STARTED__ROLE__ROLE_LOCAL_ONLY; 9384 } else if (ActiveModeManager.ROLE_SOFTAP_TETHERED.equals(role)) { 9385 return WifiStatsLog.SOFT_AP_STARTED__ROLE__ROLE_TETHERING; 9386 } 9387 Log.wtf(TAG, "getSoftApStartedRole: unknown role " + role); 9388 return WifiStatsLog.SOFT_AP_STARTED__ROLE__ROLE_UNKNOWN; 9389 } 9390 9391 private static int getSoftApStartedStaApConcurrency( 9392 boolean isStaApSupported, boolean isStaDbsSupported) { 9393 if (isStaDbsSupported) { 9394 return WifiStatsLog.SOFT_AP_STARTED__STA_AP_CONCURRENCY__STA_AP_CONCURRENCY_DBS; 9395 } 9396 if (isStaApSupported) { 9397 return WifiStatsLog.SOFT_AP_STARTED__STA_AP_CONCURRENCY__STA_AP_CONCURRENCY_SINGLE; 9398 } 9399 return WifiStatsLog.SOFT_AP_STARTED__STA_AP_CONCURRENCY__STA_AP_CONCURRENCY_UNSUPPORTED; 9400 } 9401 9402 private static int getSoftApStartedStaStatus(int staFreqMhz) { 9403 if (staFreqMhz == WifiInfo.UNKNOWN_FREQUENCY) { 9404 return WifiStatsLog.SOFT_AP_STARTED__STA_STATUS__STA_STATUS_DISCONNECTED; 9405 } 9406 if (ScanResult.is24GHz(staFreqMhz)) { 9407 return WifiStatsLog.SOFT_AP_STARTED__STA_STATUS__STA_STATUS_CONNECTED_2_GHZ; 9408 } 9409 if (ScanResult.is5GHz(staFreqMhz)) { 9410 return WifiStatsLog.SOFT_AP_STARTED__STA_STATUS__STA_STATUS_CONNECTED_5_GHZ; 9411 } 9412 if (ScanResult.is6GHz(staFreqMhz)) { 9413 return WifiStatsLog.SOFT_AP_STARTED__STA_STATUS__STA_STATUS_CONNECTED_6_GHZ; 9414 } 9415 Log.wtf(TAG, "getSoftApStartedStaStatus: unknown band for freq " + staFreqMhz); 9416 return WifiStatsLog.SOFT_AP_STARTED__STA_STATUS__STA_STATUS_UNKNOWN; 9417 } 9418 9419 private static int getSoftApStartedAuthType( 9420 @SoftApConfiguration.SecurityType int securityType) { 9421 switch (securityType) { 9422 case SoftApConfiguration.SECURITY_TYPE_OPEN: 9423 return WifiStatsLog.SOFT_AP_STARTED__AUTH_TYPE__AUTH_TYPE_NONE; 9424 case SoftApConfiguration.SECURITY_TYPE_WPA2_PSK: 9425 return WifiStatsLog.SOFT_AP_STARTED__AUTH_TYPE__AUTH_TYPE_WPA2_PSK; 9426 case SoftApConfiguration.SECURITY_TYPE_WPA3_SAE_TRANSITION: 9427 return WifiStatsLog.SOFT_AP_STARTED__AUTH_TYPE__AUTH_TYPE_SAE_TRANSITION; 9428 case SoftApConfiguration.SECURITY_TYPE_WPA3_SAE: 9429 return WifiStatsLog.SOFT_AP_STARTED__AUTH_TYPE__AUTH_TYPE_SAE; 9430 case SoftApConfiguration.SECURITY_TYPE_WPA3_OWE_TRANSITION: 9431 return WifiStatsLog.SOFT_AP_STARTED__AUTH_TYPE__AUTH_TYPE_OWE_TRANSITION; 9432 case SoftApConfiguration.SECURITY_TYPE_WPA3_OWE: 9433 return WifiStatsLog.SOFT_AP_STARTED__AUTH_TYPE__AUTH_TYPE_OWE; 9434 default: 9435 Log.wtf(TAG, "getSoftApStartedAuthType: unknown type " + securityType); 9436 return WifiStatsLog.SOFT_AP_STARTED__STA_STATUS__STA_STATUS_UNKNOWN; 9437 } 9438 } 9439 9440 /** 9441 * Writes the SoftApStarted event to WifiStatsLog. 9442 */ 9443 public void writeSoftApStartedEvent(@SoftApManager.StartResult int startResult, 9444 @NonNull ActiveModeManager.SoftApRole role, 9445 @WifiScanner.WifiBand int band1, 9446 @WifiScanner.WifiBand int band2, 9447 boolean isDbsSupported, 9448 boolean isStaApSupported, 9449 boolean isStaDbsSupported, 9450 int staFreqMhz, 9451 @SoftApConfiguration.SecurityType int securityType) { 9452 WifiStatsLog.write(WifiStatsLog.SOFT_AP_STARTED, 9453 getSoftApStartedStartResult(startResult), 9454 getSoftApStartedRole(role), 9455 band1, 9456 band2, 9457 isDbsSupported, 9458 getSoftApStartedStaApConcurrency(isStaApSupported, isStaDbsSupported), 9459 getSoftApStartedStaStatus(staFreqMhz), 9460 getSoftApStartedAuthType(securityType)); 9461 if (startResult == SoftApManager.START_RESULT_SUCCESS) { 9462 WifiStatsLog.write(WifiStatsLog.SOFT_AP_STATE_CHANGED, 9463 WifiStatsLog.SOFT_AP_STATE_CHANGED__HOTSPOT_ON__STATE_ON); 9464 } 9465 } 9466 9467 private static int getSoftApStoppedStopEvent(@SoftApManager.StopEvent int stopEvent) { 9468 switch (stopEvent) { 9469 case SoftApManager.STOP_EVENT_UNKNOWN: 9470 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_UNKNOWN; 9471 case SoftApManager.STOP_EVENT_STOPPED: 9472 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_STOPPED; 9473 case SoftApManager.STOP_EVENT_INTERFACE_DOWN: 9474 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_INTERFACE_DOWN; 9475 case SoftApManager.STOP_EVENT_INTERFACE_DESTROYED: 9476 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_INTERFACE_DESTROYED; 9477 case SoftApManager.STOP_EVENT_HOSTAPD_FAILURE: 9478 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_HOSTAPD_FAILURE; 9479 case SoftApManager.STOP_EVENT_NO_USAGE_TIMEOUT: 9480 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_NO_USAGE_TIMEOUT; 9481 default: 9482 Log.wtf(TAG, "getSoftApStoppedStopEvent: unknown StopEvent " + stopEvent); 9483 return WifiStatsLog.SOFT_AP_STOPPED__STOP_EVENT__STOP_EVENT_UNKNOWN; 9484 } 9485 } 9486 9487 private static int getSoftApStoppedRole(ActiveModeManager.SoftApRole role) { 9488 if (ActiveModeManager.ROLE_SOFTAP_LOCAL_ONLY.equals(role)) { 9489 return WifiStatsLog.SOFT_AP_STOPPED__ROLE__ROLE_LOCAL_ONLY; 9490 } else if (ActiveModeManager.ROLE_SOFTAP_TETHERED.equals(role)) { 9491 return WifiStatsLog.SOFT_AP_STOPPED__ROLE__ROLE_TETHERING; 9492 } 9493 Log.wtf(TAG, "getSoftApStoppedRole: unknown role " + role); 9494 return WifiStatsLog.SOFT_AP_STOPPED__ROLE__ROLE_UNKNOWN; 9495 } 9496 9497 private static int getSoftApStoppedStaApConcurrency( 9498 boolean isStaApSupported, boolean isStaDbsSupported) { 9499 if (isStaDbsSupported) { 9500 return WifiStatsLog.SOFT_AP_STOPPED__STA_AP_CONCURRENCY__STA_AP_CONCURRENCY_DBS; 9501 } 9502 if (isStaApSupported) { 9503 return WifiStatsLog.SOFT_AP_STOPPED__STA_AP_CONCURRENCY__STA_AP_CONCURRENCY_SINGLE; 9504 } 9505 return WifiStatsLog.SOFT_AP_STOPPED__STA_AP_CONCURRENCY__STA_AP_CONCURRENCY_UNSUPPORTED; 9506 } 9507 private static int getSoftApStoppedStaStatus(int staFreqMhz) { 9508 if (staFreqMhz == WifiInfo.UNKNOWN_FREQUENCY) { 9509 return WifiStatsLog.SOFT_AP_STOPPED__STA_STATUS__STA_STATUS_DISCONNECTED; 9510 } 9511 if (ScanResult.is24GHz(staFreqMhz)) { 9512 return WifiStatsLog.SOFT_AP_STOPPED__STA_STATUS__STA_STATUS_CONNECTED_2_GHZ; 9513 } 9514 if (ScanResult.is5GHz(staFreqMhz)) { 9515 return WifiStatsLog.SOFT_AP_STOPPED__STA_STATUS__STA_STATUS_CONNECTED_5_GHZ; 9516 } 9517 if (ScanResult.is6GHz(staFreqMhz)) { 9518 return WifiStatsLog.SOFT_AP_STOPPED__STA_STATUS__STA_STATUS_CONNECTED_6_GHZ; 9519 } 9520 Log.wtf(TAG, "getSoftApStoppedStaStatus: unknown band for freq " + staFreqMhz); 9521 return WifiStatsLog.SOFT_AP_STOPPED__STA_STATUS__STA_STATUS_UNKNOWN; 9522 } 9523 9524 private static int getSoftApStoppedAuthType( 9525 @SoftApConfiguration.SecurityType int securityType) { 9526 switch (securityType) { 9527 case SoftApConfiguration.SECURITY_TYPE_OPEN: 9528 return WifiStatsLog.SOFT_AP_STOPPED__AUTH_TYPE__AUTH_TYPE_NONE; 9529 case SoftApConfiguration.SECURITY_TYPE_WPA2_PSK: 9530 return WifiStatsLog.SOFT_AP_STOPPED__AUTH_TYPE__AUTH_TYPE_WPA2_PSK; 9531 case SoftApConfiguration.SECURITY_TYPE_WPA3_SAE_TRANSITION: 9532 return WifiStatsLog.SOFT_AP_STOPPED__AUTH_TYPE__AUTH_TYPE_SAE_TRANSITION; 9533 case SoftApConfiguration.SECURITY_TYPE_WPA3_SAE: 9534 return WifiStatsLog.SOFT_AP_STOPPED__AUTH_TYPE__AUTH_TYPE_SAE; 9535 case SoftApConfiguration.SECURITY_TYPE_WPA3_OWE_TRANSITION: 9536 return WifiStatsLog.SOFT_AP_STOPPED__AUTH_TYPE__AUTH_TYPE_OWE_TRANSITION; 9537 case SoftApConfiguration.SECURITY_TYPE_WPA3_OWE: 9538 return WifiStatsLog.SOFT_AP_STOPPED__AUTH_TYPE__AUTH_TYPE_OWE; 9539 default: 9540 Log.wtf(TAG, "getSoftApStoppedAuthType: unknown type " + securityType); 9541 return WifiStatsLog.SOFT_AP_STOPPED__STA_STATUS__STA_STATUS_UNKNOWN; 9542 } 9543 } 9544 9545 private static int getSoftApStoppedStandard(@WifiAnnotations.WifiStandard int standard) { 9546 switch (standard) { 9547 case ScanResult.WIFI_STANDARD_UNKNOWN: 9548 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_UNKNOWN; 9549 case ScanResult.WIFI_STANDARD_LEGACY: 9550 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_LEGACY; 9551 case ScanResult.WIFI_STANDARD_11N: 9552 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_11N; 9553 case ScanResult.WIFI_STANDARD_11AC: 9554 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_11AC; 9555 case ScanResult.WIFI_STANDARD_11AX: 9556 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_11AX; 9557 case ScanResult.WIFI_STANDARD_11AD: 9558 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_11AD; 9559 case ScanResult.WIFI_STANDARD_11BE: 9560 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_11BE; 9561 default: 9562 Log.wtf(TAG, "getSoftApStoppedStandard: unknown standard " + standard); 9563 return WifiStatsLog.SOFT_AP_STOPPED__STANDARD__WIFI_STANDARD_UNKNOWN; 9564 } 9565 } 9566 9567 private static int getSoftApStoppedUpstreamType(@Nullable NetworkCapabilities caps) { 9568 if (caps == null) { 9569 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_UNKNOWN; 9570 } 9571 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_VPN)) { 9572 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_WIFI)) { 9573 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR)) { 9574 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_WIFI_CELLULAR_VPN; 9575 } 9576 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_WIFI_VPN; 9577 } 9578 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR)) { 9579 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_CELLULAR_VPN; 9580 } 9581 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_BLUETOOTH)) { 9582 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_BLUETOOTH_VPN; 9583 } 9584 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_ETHERNET)) { 9585 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_ETHERNET_VPN; 9586 } 9587 } 9588 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_WIFI)) { 9589 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_WIFI; 9590 } 9591 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR)) { 9592 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_CELLULAR; 9593 } 9594 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_BLUETOOTH)) { 9595 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_BLUETOOTH; 9596 } 9597 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_ETHERNET)) { 9598 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_ETHERNET; 9599 } 9600 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_WIFI_AWARE)) { 9601 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_WIFI_AWARE; 9602 } 9603 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_LOWPAN)) { 9604 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_LOWPAN; 9605 } 9606 if (caps.hasTransport(NetworkCapabilities.TRANSPORT_TEST)) { 9607 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_TEST; 9608 } 9609 Log.wtf(TAG, "getSoftApStoppedStandard: unknown transport types for caps " 9610 + Arrays.toString(caps.getTransportTypes())); 9611 return WifiStatsLog.SOFT_AP_STOPPED__UPSTREAM_TRANSPORT__TT_UNKNOWN; 9612 } 9613 9614 /** 9615 * Writes the SoftApStoppedEvent to WifiStatsLog. 9616 */ 9617 public void writeSoftApStoppedEvent(@SoftApManager.StopEvent int stopEvent, 9618 @NonNull ActiveModeManager.SoftApRole role, 9619 @WifiScanner.WifiBand int band, 9620 boolean isDbs, 9621 boolean isStaApSupported, 9622 boolean isStaBridgedApSupported, 9623 int staFreqMhz, 9624 boolean isTimeoutEnabled, 9625 int sessionDurationSeconds, 9626 @SoftApConfiguration.SecurityType int securityType, 9627 @WifiAnnotations.WifiStandard int standard, 9628 int maxClients, 9629 boolean isDbsTimeoutEnabled, 9630 int dbsFailureBand, 9631 int dbsTimeoutBand, 9632 @Nullable NetworkCapabilities upstreamCaps) { 9633 WifiStatsLog.write(WifiStatsLog.SOFT_AP_STOPPED, 9634 getSoftApStoppedStopEvent(stopEvent), 9635 getSoftApStoppedRole(role), 9636 band, 9637 isDbs, 9638 getSoftApStoppedStaApConcurrency(isStaApSupported, isStaBridgedApSupported), 9639 getSoftApStoppedStaStatus(staFreqMhz), 9640 isTimeoutEnabled, 9641 sessionDurationSeconds, 9642 getSoftApStoppedAuthType(securityType), 9643 getSoftApStoppedStandard(standard), 9644 maxClients, 9645 isDbsTimeoutEnabled, 9646 dbsFailureBand, 9647 dbsTimeoutBand, 9648 getSoftApStoppedUpstreamType(upstreamCaps)); 9649 WifiStatsLog.write(WifiStatsLog.SOFT_AP_STATE_CHANGED, 9650 WifiStatsLog.SOFT_AP_STATE_CHANGED__HOTSPOT_ON__STATE_OFF); 9651 } 9652 } 9653