android wifi打开进程源码解析及Wifi打开失败原因分析

android wifi打开过程源码解析及Wifi打开失败原因分析

  在android中wifi打开的状态从DISABLED-->ENABLING-->ENABLED

  1 WifiSettings.java--wifi界面wifi开关

  wifi开关定义在SettingsActivity.java中,传入WifiEnabler.java,并在WifiEnabler.java中响应。 

  private SwitchBar mSwitchBar;
  public SwitchBar getSwitchBar() {
      return mSwitchBar;
  }
  mSwitchBar = (SwitchBar) findViewById(R.id.switch_bar);

  private SwitchBar mSwitchBar;
  public SwitchBar getSwitchBar() {
      return mSwitchBar;
  }
  mSwitchBar = (SwitchBar) findViewById(R.id.switch_bar);

  2 WifiEnabler.java--响应点击wifi开关

  WifiEnabler.java实际处理开关wifi的消息。

  @Override
  public void onSwitchChanged(Switch switchView, boolean isChecked) { 
      Log.d(TAG, "mWifiManager.setWifiEnabled");
      if (!mWifiManager.setWifiEnabled(isChecked)) {
          // Error
          Log.d(TAG, "set wifi enabled error");
          mSwitchBar.setEnabled(true);
          Toast.makeText(mContext, R.string.wifi_error, Toast.LENGTH_SHORT).show();
      }
    }
3 WifiManager.java和WifiService.java

  WifiEnabler.java调用WifiManager,WifiManager调用WifiService. 

  mService.setWifiEnabled(enabled);    
  public synchronized boolean setWifiEnabled(boolean enable) {       
        Slog.d(TAG, "setWifiEnabled: " + enable + " pid=" + Binder.getCallingPid()
                    + ", uid=" + Binder.getCallingUid());
        if (DBG) {
            Slog.e(TAG, "Invoking mWifiStateMachine.setWifiEnabled\n");
        }
        
        if (!mIsControllerStarted) {
            Slog.e(TAG,"WifiController is not yet started, abort setWifiEnabled");
            return false;
        }

        mWifiController.sendMessage(CMD_WIFI_TOGGLED);
        return true;
    }

4 WifiController.java

  WifiController.java处理开关wifi 的消息CMD_WIFI_TOGGLED,从ApStaDisabledState-->StaEnabledState-->DeviceActiveState,

 class ApStaDisabledState extends State {
     @Override
     public boolean processMessage(Message msg) {
         switch (msg.what) {
             case CMD_WIFI_TOGGLED:
             case CMD_AIRPLANE_TOGGLED:
                 if (mSettingsStore.isWifiToggleEnabled()) {
                     if (doDeferEnable(msg)) {
                         if (mHaveDeferredEnable) {
                             //  have 2 toggles now, inc serial number an ignore both
                             mDeferredEnableSerialNumber++;
                         }
                         mHaveDeferredEnable = !mHaveDeferredEnable;
                         break;
                     }
                     if (mDeviceIdle == false) {
                         transitionTo(mDeviceActiveState);
                     } else {
                         checkLocksAndTransitionWhenDeviceIdle();
                     }
                 } else if (mSettingsStore.isScanAlwaysAvailable()) {
                     transitionTo(mStaDisabledWithScanState);
                 }
                 break;
 } 
 class StaEnabledState extends State {
     @Override
     public void enter() {
         mWifiStateMachine.setSupplicantRunning(true);
     }
 } 
在进入StaEnabledState时由WifiStateMachine启动supplicant,进入DeviceActiveState时启动driver。

 /* Parent: StaEnabledState */
 class DeviceActiveState extends State {
     @Override
     public void enter() {
         mWifiStateMachine.setOperationalMode(WifiStateMachine.CONNECT_MODE);
         mWifiStateMachine.setDriverStart(true);
         mWifiStateMachine.setHighPerfModeEnabled(false);
     }
 } 
5 WifiStateMachine.java

  WIFI_STATE_ENABLED由SupplicantStartingState发出,   CMD_START_SUPPLICANT-->startMonitoring-->WifiMonitor.SUP_CONNECTION_EVENT-->WifiManager.WIFI_STATE_ENABLED,到此wifi开关完全打开。

 class InitialState extends State {        
     @Override
     public boolean processMessage(Message message) {            
         switch (message.what) {
             case CMD_START_SUPPLICANT:
                 if (mWifiNative.loadDriver()) {                     
                     mNwService.wifiFirmwareReload(mInterfaceName, "STA");                        
                     if(mWifiNative.startSupplicant(mP2pSupported)) {
                         setWifiState(WIFI_STATE_ENABLING);                            
                         mWifiMonitor.startMonitoring();
                         transitionTo(mSupplicantStartingState);
                     } 
                 } 
                 break;
     }
 }

 class SupplicantStartingState extends State { 
     @Override
     public boolean processMessage(Message message) {           
         switch(message.what) {
             case WifiMonitor.SUP_CONNECTION_EVENT:
                 if (DBG) log("Supplicant connection established");
                 setWifiState(WIFI_STATE_ENABLED);
                 transitionTo(mDriverStartedState);
                 break;
     }
 }

6  SoftAP打开失败wifi不能打开原因分析

  SoftAP打开过程:

  WifiService的setWifiApEnabled-->WifiController的CDM_SET_AP-->WifiStateMachine的CMD_START_AP 

 class SoftApStartingState extends State {
     @Override
     public void enter() {            
         if (message.what == CMD_START_AP) {
             final WifiConfiguration config = (WifiConfiguration) message.obj;
             if (config == null) {
                 mWifiApConfigChannel.sendMessage(CMD_REQUEST_AP_CONFIG);
             } 
         } 
     }
     @Override
     public boolean processMessage(Message message) { 
         switch(message.what) {                
             case CMD_START_AP:                
                 deferMessage(message);
                 break;
             case WifiStateMachine.CMD_RESPONSE_AP_CONFIG:
                 WifiConfiguration config = (WifiConfiguration) message.obj;
                 if (config != null) {
                     startSoftApWithConfig(config);
                 } 
                 break;                
             case CMD_START_AP_FAILURE:
                 setWifiApState(WIFI_AP_STATE_FAILED);
                 transitionTo(mInitialState);
                 break;                
            }            
     }
 }
 CMD_REQUEST_AP_CONFIG-->CMD_RESPONSE_AP_CONFIG-->startSoftApWithConfig-->CMD_START_FAILURE

 由于WifiService没有收到WIFI_AP_START_FAILED,导致WifiController处于ApEnabledState,无法接收CMD_WIFI_TOGGLED消息,从而无法进入WifiStateMachie打开WIfi。