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 android.app.ActivityManager; 20 import android.content.Context; 21 import android.net.NetworkKey; 22 import android.net.NetworkScoreManager; 23 import android.net.wifi.IApInterface; 24 import android.net.wifi.IWifiScanner; 25 import android.net.wifi.IWificond; 26 import android.net.wifi.WifiConfiguration; 27 import android.net.wifi.WifiInfo; 28 import android.net.wifi.WifiNetworkScoreCache; 29 import android.net.wifi.WifiScanner; 30 import android.os.BatteryStats; 31 import android.os.HandlerThread; 32 import android.os.IBinder; 33 import android.os.INetworkManagementService; 34 import android.os.Looper; 35 import android.os.ServiceManager; 36 import android.os.SystemProperties; 37 import android.os.UserManager; 38 import android.security.KeyStore; 39 import android.telephony.TelephonyManager; 40 import android.util.LocalLog; 41 42 import com.android.internal.R; 43 import com.android.internal.app.IBatteryStats; 44 import com.android.server.am.BatteryStatsService; 45 import com.android.server.net.DelayedDiskWrite; 46 import com.android.server.net.IpConfigStore; 47 import com.android.server.wifi.aware.WifiAwareMetrics; 48 import com.android.server.wifi.hotspot2.PasspointManager; 49 import com.android.server.wifi.hotspot2.PasspointNetworkEvaluator; 50 import com.android.server.wifi.hotspot2.PasspointObjectFactory; 51 import com.android.server.wifi.p2p.SupplicantP2pIfaceHal; 52 import com.android.server.wifi.p2p.WifiP2pMonitor; 53 import com.android.server.wifi.p2p.WifiP2pNative; 54 import com.android.server.wifi.util.WifiPermissionsUtil; 55 import com.android.server.wifi.util.WifiPermissionsWrapper; 56 57 /** 58 * WiFi dependency injector. To be used for accessing various WiFi class instances and as a 59 * handle for mock injection. 60 * 61 * Some WiFi class instances currently depend on having a Looper from a HandlerThread that has 62 * been started. To accommodate this, we have a two-phased approach to initialize and retrieve 63 * an instance of the WifiInjector. 64 */ 65 public class WifiInjector { 66 private static final String BOOT_DEFAULT_WIFI_COUNTRY_CODE = "ro.boot.wificountrycode"; 67 private static final String WIFICOND_SERVICE_NAME = "wificond"; 68 69 static WifiInjector sWifiInjector = null; 70 71 private final Context mContext; 72 private final FrameworkFacade mFrameworkFacade = new FrameworkFacade(); 73 private final HandlerThread mWifiServiceHandlerThread; 74 private final HandlerThread mWifiStateMachineHandlerThread; 75 private final WifiTrafficPoller mTrafficPoller; 76 private final WifiCountryCode mCountryCode; 77 private final BackupManagerProxy mBackupManagerProxy = new BackupManagerProxy(); 78 private final WifiApConfigStore mWifiApConfigStore; 79 private final WifiNative mWifiNative; 80 private final WifiMonitor mWifiMonitor; 81 private final WifiP2pNative mWifiP2pNative; 82 private final WifiP2pMonitor mWifiP2pMonitor; 83 private final SupplicantStaIfaceHal mSupplicantStaIfaceHal; 84 private final SupplicantP2pIfaceHal mSupplicantP2pIfaceHal; 85 private final WifiVendorHal mWifiVendorHal; 86 private final WifiStateMachine mWifiStateMachine; 87 private final WifiSettingsStore mSettingsStore; 88 private final WifiCertManager mCertManager; 89 private final OpenNetworkNotifier mOpenNetworkNotifier; 90 private final WifiLockManager mLockManager; 91 private final WifiController mWifiController; 92 private final WificondControl mWificondControl; 93 private final Clock mClock = new Clock(); 94 private final WifiMetrics mWifiMetrics; 95 private final WifiLastResortWatchdog mWifiLastResortWatchdog; 96 private final PropertyService mPropertyService = new SystemPropertyService(); 97 private final BuildProperties mBuildProperties = new SystemBuildProperties(); 98 private final KeyStore mKeyStore = KeyStore.getInstance(); 99 private final WifiBackupRestore mWifiBackupRestore; 100 private final WifiMulticastLockManager mWifiMulticastLockManager; 101 private final WifiConfigStore mWifiConfigStore; 102 private final WifiKeyStore mWifiKeyStore; 103 private final IpConfigStore mIpConfigStore; 104 private final WifiConfigManager mWifiConfigManager; 105 private final WifiConnectivityHelper mWifiConnectivityHelper; 106 private final LocalLog mConnectivityLocalLog; 107 private final WifiNetworkSelector mWifiNetworkSelector; 108 private final SavedNetworkEvaluator mSavedNetworkEvaluator; 109 private final PasspointNetworkEvaluator mPasspointNetworkEvaluator; 110 private final ScoredNetworkEvaluator mScoredNetworkEvaluator; 111 private final WifiNetworkScoreCache mWifiNetworkScoreCache; 112 private final NetworkScoreManager mNetworkScoreManager; 113 private WifiScanner mWifiScanner; 114 private final WifiPermissionsWrapper mWifiPermissionsWrapper; 115 private final WifiPermissionsUtil mWifiPermissionsUtil; 116 private final PasspointManager mPasspointManager; 117 private final SIMAccessor mSimAccessor; 118 private HandlerThread mWifiAwareHandlerThread; 119 private HalDeviceManager mHalDeviceManager; 120 private final IBatteryStats mBatteryStats; 121 private final WifiStateTracker mWifiStateTracker; 122 private final Runtime mJavaRuntime; 123 private final SelfRecovery mSelfRecovery; 124 125 private final boolean mUseRealLogger; 126 WifiInjector(Context context)127 public WifiInjector(Context context) { 128 if (context == null) { 129 throw new IllegalStateException( 130 "WifiInjector should not be initialized with a null Context."); 131 } 132 133 if (sWifiInjector != null) { 134 throw new IllegalStateException( 135 "WifiInjector was already created, use getInstance instead."); 136 } 137 138 sWifiInjector = this; 139 140 mContext = context; 141 mUseRealLogger = mContext.getResources().getBoolean( 142 R.bool.config_wifi_enable_wifi_firmware_debugging); 143 mSettingsStore = new WifiSettingsStore(mContext); 144 mWifiPermissionsWrapper = new WifiPermissionsWrapper(mContext); 145 mNetworkScoreManager = mContext.getSystemService(NetworkScoreManager.class); 146 mWifiNetworkScoreCache = new WifiNetworkScoreCache(mContext); 147 mNetworkScoreManager.registerNetworkScoreCache(NetworkKey.TYPE_WIFI, 148 mWifiNetworkScoreCache, NetworkScoreManager.CACHE_FILTER_NONE); 149 mWifiPermissionsUtil = new WifiPermissionsUtil(mWifiPermissionsWrapper, mContext, 150 mSettingsStore, UserManager.get(mContext), mNetworkScoreManager, this); 151 mWifiBackupRestore = new WifiBackupRestore(mWifiPermissionsUtil); 152 mBatteryStats = IBatteryStats.Stub.asInterface(mFrameworkFacade.getService( 153 BatteryStats.SERVICE_NAME)); 154 mWifiStateTracker = new WifiStateTracker(mBatteryStats); 155 // Now create and start handler threads 156 mWifiServiceHandlerThread = new HandlerThread("WifiService"); 157 mWifiServiceHandlerThread.start(); 158 mWifiStateMachineHandlerThread = new HandlerThread("WifiStateMachine"); 159 mWifiStateMachineHandlerThread.start(); 160 Looper wifiStateMachineLooper = mWifiStateMachineHandlerThread.getLooper(); 161 WifiAwareMetrics awareMetrics = new WifiAwareMetrics(mClock); 162 mWifiMetrics = new WifiMetrics(mClock, wifiStateMachineLooper, awareMetrics); 163 // Modules interacting with Native. 164 mWifiMonitor = new WifiMonitor(this); 165 mHalDeviceManager = new HalDeviceManager(); 166 mWifiVendorHal = 167 new WifiVendorHal(mHalDeviceManager, mWifiStateMachineHandlerThread.getLooper()); 168 mSupplicantStaIfaceHal = new SupplicantStaIfaceHal(mContext, mWifiMonitor); 169 mWificondControl = new WificondControl(this, mWifiMonitor, 170 new CarrierNetworkConfig(mContext)); 171 mWifiNative = new WifiNative(SystemProperties.get("wifi.interface", "wlan0"), 172 mWifiVendorHal, mSupplicantStaIfaceHal, mWificondControl); 173 mWifiP2pMonitor = new WifiP2pMonitor(this); 174 mSupplicantP2pIfaceHal = new SupplicantP2pIfaceHal(mWifiP2pMonitor); 175 mWifiP2pNative = new WifiP2pNative(SystemProperties.get("wifi.direct.interface", "p2p0"), 176 mSupplicantP2pIfaceHal); 177 178 // Now get instances of all the objects that depend on the HandlerThreads 179 mTrafficPoller = new WifiTrafficPoller(mContext, mWifiServiceHandlerThread.getLooper(), 180 mWifiNative.getInterfaceName()); 181 mCountryCode = new WifiCountryCode(mWifiNative, 182 SystemProperties.get(BOOT_DEFAULT_WIFI_COUNTRY_CODE), 183 mContext.getResources() 184 .getBoolean(R.bool.config_wifi_revert_country_code_on_cellular_loss)); 185 mWifiApConfigStore = new WifiApConfigStore(mContext, mBackupManagerProxy); 186 187 // WifiConfigManager/Store objects and their dependencies. 188 // New config store 189 mWifiKeyStore = new WifiKeyStore(mKeyStore); 190 mWifiConfigStore = new WifiConfigStore( 191 mContext, wifiStateMachineLooper, mClock, 192 WifiConfigStore.createSharedFile()); 193 // Legacy config store 194 DelayedDiskWrite writer = new DelayedDiskWrite(); 195 mIpConfigStore = new IpConfigStore(writer); 196 // Config Manager 197 mWifiConfigManager = new WifiConfigManager(mContext, mClock, 198 UserManager.get(mContext), TelephonyManager.from(mContext), 199 mWifiKeyStore, mWifiConfigStore, mWifiPermissionsUtil, 200 mWifiPermissionsWrapper, new NetworkListStoreData(mContext), 201 new DeletedEphemeralSsidsStoreData()); 202 mWifiMetrics.setWifiConfigManager(mWifiConfigManager); 203 mWifiConnectivityHelper = new WifiConnectivityHelper(mWifiNative); 204 mConnectivityLocalLog = new LocalLog(ActivityManager.isLowRamDeviceStatic() ? 256 : 512); 205 mWifiNetworkSelector = new WifiNetworkSelector(mContext, mWifiConfigManager, mClock, 206 mConnectivityLocalLog); 207 mWifiMetrics.setWifiNetworkSelector(mWifiNetworkSelector); 208 mSavedNetworkEvaluator = new SavedNetworkEvaluator(mContext, 209 mWifiConfigManager, mClock, mConnectivityLocalLog, mWifiConnectivityHelper); 210 mScoredNetworkEvaluator = new ScoredNetworkEvaluator(context, wifiStateMachineLooper, 211 mFrameworkFacade, mNetworkScoreManager, mWifiConfigManager, mConnectivityLocalLog, 212 mWifiNetworkScoreCache); 213 mSimAccessor = new SIMAccessor(mContext); 214 mPasspointManager = new PasspointManager(mContext, mWifiNative, mWifiKeyStore, mClock, 215 mSimAccessor, new PasspointObjectFactory(), mWifiConfigManager, mWifiConfigStore, 216 mWifiMetrics); 217 mPasspointNetworkEvaluator = new PasspointNetworkEvaluator( 218 mPasspointManager, mWifiConfigManager, mConnectivityLocalLog); 219 mWifiMetrics.setPasspointManager(mPasspointManager); 220 // mWifiStateMachine has an implicit dependency on mJavaRuntime due to WifiDiagnostics. 221 mJavaRuntime = Runtime.getRuntime(); 222 mWifiStateMachine = new WifiStateMachine(mContext, mFrameworkFacade, 223 wifiStateMachineLooper, UserManager.get(mContext), 224 this, mBackupManagerProxy, mCountryCode, mWifiNative, 225 new WrongPasswordNotifier(mContext, mFrameworkFacade)); 226 mCertManager = new WifiCertManager(mContext); 227 mOpenNetworkNotifier = new OpenNetworkNotifier(mContext, 228 mWifiStateMachineHandlerThread.getLooper(), mFrameworkFacade, mClock, mWifiMetrics, 229 mWifiConfigManager, mWifiConfigStore, mWifiStateMachine, 230 new OpenNetworkRecommender(), 231 new ConnectToNetworkNotificationBuilder(mContext, mFrameworkFacade)); 232 mLockManager = new WifiLockManager(mContext, BatteryStatsService.getService()); 233 mWifiController = new WifiController(mContext, mWifiStateMachine, mSettingsStore, 234 mLockManager, mWifiServiceHandlerThread.getLooper(), mFrameworkFacade); 235 mSelfRecovery = new SelfRecovery(mWifiController, mClock); 236 mWifiLastResortWatchdog = new WifiLastResortWatchdog(mSelfRecovery, mWifiMetrics); 237 mWifiMulticastLockManager = new WifiMulticastLockManager(mWifiStateMachine, 238 BatteryStatsService.getService()); 239 } 240 241 /** 242 * Obtain an instance of the WifiInjector class. 243 * 244 * This is the generic method to get an instance of the class. The first instance should be 245 * retrieved using the getInstanceWithContext method. 246 */ getInstance()247 public static WifiInjector getInstance() { 248 if (sWifiInjector == null) { 249 throw new IllegalStateException( 250 "Attempted to retrieve a WifiInjector instance before constructor was called."); 251 } 252 return sWifiInjector; 253 } 254 getUserManager()255 public UserManager getUserManager() { 256 return UserManager.get(mContext); 257 } 258 getWifiMetrics()259 public WifiMetrics getWifiMetrics() { 260 return mWifiMetrics; 261 } 262 getSupplicantStaIfaceHal()263 public SupplicantStaIfaceHal getSupplicantStaIfaceHal() { 264 return mSupplicantStaIfaceHal; 265 } 266 getBackupManagerProxy()267 public BackupManagerProxy getBackupManagerProxy() { 268 return mBackupManagerProxy; 269 } 270 getFrameworkFacade()271 public FrameworkFacade getFrameworkFacade() { 272 return mFrameworkFacade; 273 } 274 getWifiServiceHandlerThread()275 public HandlerThread getWifiServiceHandlerThread() { 276 return mWifiServiceHandlerThread; 277 } 278 getWifiStateMachineHandlerThread()279 public HandlerThread getWifiStateMachineHandlerThread() { 280 return mWifiStateMachineHandlerThread; 281 } 282 getWifiTrafficPoller()283 public WifiTrafficPoller getWifiTrafficPoller() { 284 return mTrafficPoller; 285 } 286 getWifiCountryCode()287 public WifiCountryCode getWifiCountryCode() { 288 return mCountryCode; 289 } 290 getWifiApConfigStore()291 public WifiApConfigStore getWifiApConfigStore() { 292 return mWifiApConfigStore; 293 } 294 getWifiStateMachine()295 public WifiStateMachine getWifiStateMachine() { 296 return mWifiStateMachine; 297 } 298 getWifiSettingsStore()299 public WifiSettingsStore getWifiSettingsStore() { 300 return mSettingsStore; 301 } 302 getWifiCertManager()303 public WifiCertManager getWifiCertManager() { 304 return mCertManager; 305 } 306 getWifiLockManager()307 public WifiLockManager getWifiLockManager() { 308 return mLockManager; 309 } 310 getWifiController()311 public WifiController getWifiController() { 312 return mWifiController; 313 } 314 getWifiLastResortWatchdog()315 public WifiLastResortWatchdog getWifiLastResortWatchdog() { 316 return mWifiLastResortWatchdog; 317 } 318 getClock()319 public Clock getClock() { 320 return mClock; 321 } 322 getPropertyService()323 public PropertyService getPropertyService() { 324 return mPropertyService; 325 } 326 getBuildProperties()327 public BuildProperties getBuildProperties() { 328 return mBuildProperties; 329 } 330 getKeyStore()331 public KeyStore getKeyStore() { 332 return mKeyStore; 333 } 334 getWifiBackupRestore()335 public WifiBackupRestore getWifiBackupRestore() { 336 return mWifiBackupRestore; 337 } 338 getWifiMulticastLockManager()339 public WifiMulticastLockManager getWifiMulticastLockManager() { 340 return mWifiMulticastLockManager; 341 } 342 getWifiConfigManager()343 public WifiConfigManager getWifiConfigManager() { 344 return mWifiConfigManager; 345 } 346 getPasspointManager()347 public PasspointManager getPasspointManager() { 348 return mPasspointManager; 349 } 350 makeTelephonyManager()351 public TelephonyManager makeTelephonyManager() { 352 // may not be available when WiFi starts 353 return (TelephonyManager) mContext.getSystemService(Context.TELEPHONY_SERVICE); 354 } 355 getWifiStateTracker()356 public WifiStateTracker getWifiStateTracker() { 357 return mWifiStateTracker; 358 } 359 makeWificond()360 public IWificond makeWificond() { 361 // We depend on being able to refresh our binder in WifiStateMachine, so don't cache it. 362 IBinder binder = ServiceManager.getService(WIFICOND_SERVICE_NAME); 363 return IWificond.Stub.asInterface(binder); 364 } 365 366 /** 367 * Create a SoftApManager. 368 * @param nmService NetworkManagementService allowing SoftApManager to listen for interface 369 * changes 370 * @param listener listener for SoftApManager 371 * @param apInterface network interface to start hostapd against 372 * @param config softAp WifiConfiguration 373 * @return an instance of SoftApManager 374 */ makeSoftApManager(INetworkManagementService nmService, SoftApManager.Listener listener, IApInterface apInterface, WifiConfiguration config)375 public SoftApManager makeSoftApManager(INetworkManagementService nmService, 376 SoftApManager.Listener listener, 377 IApInterface apInterface, 378 WifiConfiguration config) { 379 return new SoftApManager(mWifiServiceHandlerThread.getLooper(), 380 mWifiNative, mCountryCode.getCountryCode(), 381 listener, apInterface, nmService, 382 mWifiApConfigStore, config, mWifiMetrics); 383 } 384 385 /** 386 * Create a WifiLog instance. 387 * @param tag module name to include in all log messages 388 */ makeLog(String tag)389 public WifiLog makeLog(String tag) { 390 return new LogcatLog(tag); 391 } 392 makeWifiDiagnostics(WifiNative wifiNative)393 public BaseWifiDiagnostics makeWifiDiagnostics(WifiNative wifiNative) { 394 if (mUseRealLogger) { 395 return new WifiDiagnostics( 396 mContext, this, mWifiStateMachine, wifiNative, mBuildProperties, 397 new LastMileLogger(this)); 398 } else { 399 return new BaseWifiDiagnostics(wifiNative); 400 } 401 } 402 403 /** 404 * Obtain an instance of WifiScanner. 405 * If it was not already created, then obtain an instance. Note, this must be done lazily since 406 * WifiScannerService is separate and created later. 407 */ getWifiScanner()408 public synchronized WifiScanner getWifiScanner() { 409 if (mWifiScanner == null) { 410 mWifiScanner = new WifiScanner(mContext, 411 IWifiScanner.Stub.asInterface(ServiceManager.getService( 412 Context.WIFI_SCANNING_SERVICE)), 413 mWifiStateMachineHandlerThread.getLooper()); 414 } 415 return mWifiScanner; 416 } 417 418 /** 419 * Obtain a new instance of WifiConnectivityManager. 420 * 421 * Create and return a new WifiConnectivityManager. 422 * @param wifiInfo WifiInfo object for updating wifi state. 423 * @param hasConnectionRequests boolean indicating if WifiConnectivityManager to start 424 * immediately based on connection requests. 425 */ makeWifiConnectivityManager(WifiInfo wifiInfo, boolean hasConnectionRequests)426 public WifiConnectivityManager makeWifiConnectivityManager(WifiInfo wifiInfo, 427 boolean hasConnectionRequests) { 428 return new WifiConnectivityManager(mContext, mWifiStateMachine, getWifiScanner(), 429 mWifiConfigManager, wifiInfo, mWifiNetworkSelector, mWifiConnectivityHelper, 430 mWifiLastResortWatchdog, mOpenNetworkNotifier, mWifiMetrics, 431 mWifiStateMachineHandlerThread.getLooper(), mClock, mConnectivityLocalLog, 432 hasConnectionRequests, mFrameworkFacade, mSavedNetworkEvaluator, 433 mScoredNetworkEvaluator, mPasspointNetworkEvaluator); 434 } 435 getWifiPermissionsUtil()436 public WifiPermissionsUtil getWifiPermissionsUtil() { 437 return mWifiPermissionsUtil; 438 } 439 getWifiPermissionsWrapper()440 public WifiPermissionsWrapper getWifiPermissionsWrapper() { 441 return mWifiPermissionsWrapper; 442 } 443 444 /** 445 * Returns a singleton instance of a HandlerThread for injection. Uses lazy initialization. 446 * 447 * TODO: share worker thread with other Wi-Fi handlers (b/27924886) 448 */ getWifiAwareHandlerThread()449 public HandlerThread getWifiAwareHandlerThread() { 450 if (mWifiAwareHandlerThread == null) { // lazy initialization 451 mWifiAwareHandlerThread = new HandlerThread("wifiAwareService"); 452 mWifiAwareHandlerThread.start(); 453 } 454 return mWifiAwareHandlerThread; 455 } 456 457 /** 458 * Returns a single instance of HalDeviceManager for injection. 459 */ getHalDeviceManager()460 public HalDeviceManager getHalDeviceManager() { 461 return mHalDeviceManager; 462 } 463 getJavaRuntime()464 public Runtime getJavaRuntime() { 465 return mJavaRuntime; 466 } 467 getWifiNative()468 public WifiNative getWifiNative() { 469 return mWifiNative; 470 } 471 getWifiMonitor()472 public WifiMonitor getWifiMonitor() { 473 return mWifiMonitor; 474 } 475 getWifiP2pNative()476 public WifiP2pNative getWifiP2pNative() { 477 return mWifiP2pNative; 478 } 479 getWifiP2pMonitor()480 public WifiP2pMonitor getWifiP2pMonitor() { 481 return mWifiP2pMonitor; 482 } 483 getSelfRecovery()484 public SelfRecovery getSelfRecovery() { 485 return mSelfRecovery; 486 } 487 } 488