wifi相关的文件位置:

WIFISettings应用程序位于

packages/apps/Settings/src/com/android/settings/wifi/

JAVA部分:

frameworks/base/services/java/com/android/server/

frameworks/base/wifi/java/android/net/wifi/

JNI部分:

frameworks/base/core/jni/android_net_wifi_Wifi.cpp

wifi管理库。

hardware/libhardware_legary/wifi/

wifi用户空间的程序和库:

external/wpa_supplicant/

生成库libwpaclient.so和守护进程wpa_supplicant

调用流程:

wifi模块的初始化:

frameworks/base/services/java/com/android/server/SystemServer.Java

SystemServer 启动的时候,会生成一个ConnectivityService的实例,

classServerThreadextends Thread {

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
try {

Slog.i(TAG,"Connectivity Service");

connectivity=ConnectivityService.getInstance(context);

ServiceManager.addService(Context.CONNECTIVITY_SERVICE,connectivity);

} catch(Throwable e) {

Slog.e(TAG,"Failure starting Connectivity Service", e);

}

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

}

其中ConnectivityService.getInstance(context); 对应于(frameworks/base/services/java/com/android/server/ConnectivityService.JavaConnectivityService.Java

下面看下ConnectivityService.Java中的

publicstatic ConnectivityServicegetInstance(Context context) {

returnConnectivityThread.getServiceInstance(context);

}函数,继续往下看:

publicstatic ConnectivityService getServiceInstance(Context context) {

ConnectivityThreadthread =newConnectivityThread(context);

thread.start();

synchronized(thread) {

while(sServiceInstance == null) {

try {

// Wait until sServiceInstance has beeninitialized.

thread.wait();

} catch (InterruptedExceptionignore) {

Slog.e(TAG,

"UnexpectedInterruptedException while waiting"+

" forConnectivityService thread");

}

}

}

return sServiceInstance;

}

}

继续往下跟:

privatestatic classConnectivityThreadextends Thread {

privateContext mContext;

privateConnectivityThread(Context context) {

super("ConnectivityThread");

mContext= context;

}

@Override

publicvoid run() {

Looper.prepare();

synchronized(this) {

sServiceInstance=newConnectivityService(mContext);

notifyAll();

}

Looper.loop();

}

publicstatic ConnectivityService getServiceInstance(Context context) {

ConnectivityThreadthread = new ConnectivityThread(context);

thread.start();

synchronized(thread) {

while (sServiceInstance== null) {

try {

// Wait untilsServiceInstance has been initialized.

thread.wait();

} catch(InterruptedException ignore) {

Slog.e(TAG,

"UnexpectedInterruptedException while waiting"+

" forConnectivityService thread");

}

}

}

returnsServiceInstance;

}

}

继续newConnectivityService(mContext)

privateConnectivityService(Context context) {

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

for(int netType : mPriorityList) {

switch(mNetAttributes[netType].mRadio) {

caseConnectivityManager.TYPE_WIFI:

Slog.v(TAG,"Starting Wifi Service.");

WifiStateTracker wst =newWifiStateTracker(context, mHandler);

WifiServicewifiService =newWifiService(context, wst);

ServiceManager.addService(Context.WIFI_SERVICE,wifiService);

wifiService.startWifi();//启动wifiservice

mNetTrackers[ConnectivityManager.TYPE_WIFI]= wst;

wst.startMonitoring();//启动Monitoring

break;。。。。。

}//endfor

。。。。。。。。。。。。。。。。。。。。。。。。。。

}

到这里模块初始化的工作完成,具体流程图如下:

WifiStateTracker会创建 WifiMonitor 接收来自底层的事件,WifiService WifiMonitor 是整个模块的核心。WifiService 负责启动关闭wpa_supplicant、启动关闭 WifiMonitor 监视线程和把命令下发给 wpa_supplicant,WifiMonitor 则负责从wpa_supplicant接收事件通知。

也就是说WifiService负责wifi整个流程的控制,而WifiMonitor负责监视底层的事件。

此时WifiService starting up withWi-Fidisabled

Wifi模块的启动(Enable):

packages/apps/Settings/src/com/android/settings/wifi/WirelessSettings.java

WirelessSettings在初始化的时候配置了由WifiEnabler 来处理Wifi 按钮,

protected void onCreate(BundlesavedInstanceState) {

super.onCreate(savedInstanceState);

mWifiManager = (WifiManager)getSystemService(Context.WIFI_SERVICE);

if (getIntent().getBooleanExtra("only_access_points",false)) {

addPreferencesFromResource(R.xml.wifi_access_points);

} else {

addPreferencesFromResource(R.xml.wifi_settings);

mWifiEnabler= new WifiEnabler(this,

(CheckBoxPreference)findPreference("enable_wifi"));

mNotifyOpenNetworks =

(CheckBoxPreference)findPreference("notify_open_networks");

mNotifyOpenNetworks.setChecked(Secure.getInt(getContentResolver(),

Secure.WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON,0) == 1);

}

mAccessPoints = (ProgressCategory)findPreference("access_points");

mAccessPoints.setOrderingAsAdded(false);

mAddNetwork =findPreference("add_network");

registerForContextMenu(getListView());

}

然后调用:packages/apps/Settings/src/com/android/settings/wifi/WifiEnabler.java

publicclassWifiEnabler implements Preference.OnPreferenceChangeListener {

。。。。。。。。。。。。。。。。。。。。。。

public boolean onPreferenceChange(Preferencepreference, Object value) {

。。。。。。。。。。。。。。。。。。。。。。。。。。。

if (mWifiManager.setWifiEnabled(enable)){

mCheckBox.setEnabled(false);

} else {

mCheckBox.setSummary(R.string.wifi_error);

}

。。。。。。。。。。。。。。。。。。。。。。

}

。。。。。。。。。。。。。。。。。。。。。

}

调用:

packages/apps/Settings/src/com/android/settings/wifi/WifiManager.java

public boolean setWifiEnabled(booleanenabled) {

try {

returnmService.setWifiEnabled(enabled);

} catch(RemoteException e) {

returnfalse;

}

}

当用户按下 Wifi 按钮后,Android 会调用WifiEnabler onPreferenceChange,再由 WifiEnabler调用WifiManager setWifiEnabled接口函数,通过 AIDL,实际调用的是 WifiService setWifiEnabled函数,WifiService 接着向自身发送一条MESSAGE_ENABLE_WIFI 消息,在处理该消息的代码中做真正的使能工作:首先装载 WIFI 内核模块(该模块的位置硬编码为"/system/lib/modules/wlan.ko"), wpa_supplicant ( "/data/misc/wifi/wpa_supplicant.conf")再通过 WifiStateTracker 来启动WifiMonitor 中的监视线程。

WifiServiceWifiService.java收到MESSAGE_ENABLE_WIFI 消息后的操作如下:

AIDL:

AndroidInterface Definition Language,Android接口描述语言。Android系统中的进程之间不能共享内存,因此,需要提供一些机制在不同进程之间进行数据通信。

为了使其他的应用程序也可以访问本应用程序提供的服务,Android系统采用了远程过程调用(RemoteProcedure CallRPC)方式来实现。与很多其他的基于RPC的解决方案一样,Android使用一种接口定义语言(InterfaceDefinitionLanguageIDL)来公开服务的接口。因此,可以将这种可以跨进程访问的服务称为AIDLAndroid Interface Definition Language)服务。

接下来继续道wifiService.Java

frameworks/base/services/java/com/android/server/wifiService.Java

public booleansetWifiEnabled(booleanenable) {

enforceChangePermission();

if (mWifiHandler == null) return false;

synchronized (mWifiHandler) {

// caller may not have WAKE_LOCKpermission - it's not required here

long ident =Binder.clearCallingIdentity();

sWakeLock.acquire();

Binder.restoreCallingIdentity(ident);

mLastEnableUid =Binder.getCallingUid();

// set a flag if the user isenabling Wifi while in airplane mode

mAirplaneModeOverwridden = (enable&& isAirplaneModeOn() &&isAirplaneToggleable());

sendEnableMessage(enable,true,Binder.getCallingUid());//heresend a mesage to himself

}

return true;

}

继续往下:

private voidsendEnableMessage(booleanenable,boolean persist, int uid) {

Message msg= Message.obtain(mWifiHandler,

(enable ?MESSAGE_ENABLE_WIFI : MESSAGE_DISABLE_WIFI),

(persist ? 1 : 0), uid);

msg.sendToTarget();

}

WifiHandler会收到消息:

privateclassWifiHandlerextendsHandler {

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

publicvoidhandleMessage(Message msg) {

switch (msg.what) {

case MESSAGE_ENABLE_WIFI:

setWifiEnabledBlocking(true,msg.arg1 == 1,msg.arg2);

if (mWifiWatchdogService ==null) {

mWifiWatchdogService= newWifiWatchdogService(mContext, mWifiStateTracker);

}

sWakeLock.release();

break;

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

}

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

}

privatebooleansetWifiEnabledBlocking(booleanenable,boolean persist, int uid) {

。。。。。。。。。。。。

setWifiEnabledState(enable ?WIFI_STATE_ENABLING : WIFI_STATE_DISABLING, uid);

if(enable) {

if (!mWifiStateTracker.loadDriver()){

Slog.e(TAG, "Failed toload Wi-Fi driver.");

setWifiEnabledState(WIFI_STATE_UNKNOWN,uid);

return false;

}

if (!mWifiStateTracker.startSupplicant()){

mWifiStateTracker.unloadDriver();

Slog.e(TAG, "Failed tostart supplicant daemon.");

setWifiEnabledState(WIFI_STATE_UNKNOWN,uid);

return false;

}

registerForBroadcasts();

mWifiStateTracker.startEventLoop();

} else {

mContext.unregisterReceiver(mReceiver);

// Remove notification (it willno-op if it isn't visible)

mWifiStateTracker.setNotificationVisible(false,0,false, 0);

booleanfailedToStopSupplicantOrUnloadDriver = false;

if (!mWifiStateTracker.stopSupplicant()){

Slog.e(TAG, "Failed tostop supplicant daemon.");

setWifiEnabledState(WIFI_STATE_UNKNOWN,uid);

failedToStopSupplicantOrUnloadDriver= true;

}

/**

* Reset connections and disableinterface

* before we unload the driver

*/

mWifiStateTracker.resetConnections(true);

if (!mWifiStateTracker.unloadDriver()){

Slog.e(TAG, "Failed tounload Wi-Fi driver.");

if(!failedToStopSupplicantOrUnloadDriver) {

setWifiEnabledState(WIFI_STATE_UNKNOWN, uid);

failedToStopSupplicantOrUnloadDriver= true;

}

}

if(failedToStopSupplicantOrUnloadDriver) {

return false;

}

}

。。。。。。。。。。。。。。。。。。。。。。

}

具体流程如下流程图所示:

扫描查找热点(AP

上一节中讲到Wifi模块开启后会对外发送WIFI_STATE_CHANGED_ACTIONWifiLayer中注册了ActionReceiver
WifiLayer收到此Action后开始scan的流程,具体如下

wpa_supplicant 处理完SCAN 命令后,它会向控制通道发送事件通知扫描完成,从wifi_wait_for_event函数会接收到该事件,由此WifiMonitor 中的MonitorThread会被执行来出来这个事件

配置 AP 参数
当用户在WifiSettings 界面上选择了一个AP 后,会显示配置AP 参数的一个对话框

Wifi连接

具体流程参见以下流程图

IP地址的配置
流程如图

到此结束

更多相关文章

  1. android webkit 初始化流程
  2. Android系统启动流程 -4
  3. Android 触屏事件处理_手势识别
  4. android核心模块及相关技术
  5. Android启动流程分析(十) action的执行和service的启动
  6. Android系统启动流程 -- android
  7. Android (6.0) 系统启动流程梳理

随机推荐

  1. Android测试教程(16):monkeyrunner简介
  2. android学习中遇到的问题
  3. Android(安卓)切换主题 (二)
  4. Android高手进阶教程(十六)---Android中I
  5. Android(安卓)资源文件使用方法详解
  6. android开发的3种方式
  7. android事件拦截处理机制详解
  8. Android(安卓)数据存储五种方式使用与总
  9. Android(安卓)采用HttpClient提交数据到
  10. Android利用已有控件实现自定义控件