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