Wifi模塊
(1)
(2)
一,Wifi模塊相關(guān)文件解析
1)
packages/apps/Settings/src/com/android/settings/wifi wifisettings.java
{
private final IntentFilter mFilter;
//廣播接收器,用來接收消息并做響應(yīng)的處理工作
private final BroadcastReceiver mReceiver;
//這是一個(gè)掃描類,會(huì)在用戶手動(dòng)掃描
private final Scanner mScanner;
private WifiInfo mLastInfo;
private WifiManager mWifiManager;
//這個(gè)類主要實(shí)現(xiàn)Wifi的開閉工作
private WifiEnabler mWifiEnabler;
//AP
private AccessPoint mSelected;
private WifiDialog mDialog;
……
}
public WifiSettings() {
mFilter = new IntentFilter();
//intent機(jī)制中的intent消息過濾器,下面添加可以處理的動(dòng)作
//注冊(cè)了廣播接收器,用來處理接收到的消息事件
}
……
mWifiManager = (WifiManager) getSystemService(Context.WIFI_SERVICE);
mWifiEnabler = new WifiEnabler(this,
……
2)
packages/apps/Settings/src/com/android/settings/wifi/WifiEnabler.java
private final Context mContext;
private final CheckBoxPreference mCheckBox;
//兩個(gè)重要成員
private final WifiManager mWifiManager;
private final IntentFilter mIntentFilter;
該類中定義了幾個(gè)重要的函數(shù)onPreferenceChange,handleWifiStateChanged和handleStateChanged,onPreferenceChange用來處理按下的Enbler鍵,它會(huì)調(diào)用mWifiManager.setWifiEnabled(enable),另外兩個(gè)用來處理接受的消息事件。
public WifiEnabler(Context context, CheckBoxPreference checkBox) {
}
這里可以總結(jié)為:如果上層需要監(jiān)聽或收到下層的消息,那么就要通過定義一個(gè)BroadcastReciever,并將它注冊(cè),當(dāng)然在接受到消息后應(yīng)該有處理消息的函數(shù),然后在onReciever函數(shù)中根據(jù)消息調(diào)用相應(yīng)的處理函數(shù),這里的消息通知機(jī)制是Intent,在BroadcastReciever類的onReciever函數(shù)的參數(shù)中可以看出。
該類成員函數(shù)的也是通過調(diào)用mWifimanager的接口來實(shí)現(xiàn)的。
//WifiService
IWifiManager mService;
IWifiManager mService和Handler mHandler,這個(gè)類擁有了一個(gè)WifiService實(shí)例,就可以通過它進(jìn)行一系列的調(diào)用;WifiManager中定義了的wifi和ap的狀態(tài),這些狀態(tài)會(huì)在其他很多類中有使用;然后定義了大量的函數(shù),這些函數(shù)幾乎都是對(duì)WifiService接口函數(shù)的封裝,直接調(diào)用WifiService的函數(shù)。
該類的構(gòu)造函數(shù)很簡(jiǎn)單:
public WifiManager(IWifiManager service, Handler handler) {
該類中還定義了一個(gè)WifiLock類,這個(gè)類用來保證在有應(yīng)用程序使用Wifi無線電傳輸數(shù)據(jù)時(shí),wifi radio可用,即當(dāng)一個(gè)應(yīng)用程序使用wifi的radio進(jìn)行無線電數(shù)據(jù)傳輸時(shí),就要先獲得這個(gè)鎖,如果該鎖已被其他程序占有,就要等到該鎖被釋放后才能獲得,只用當(dāng)所有持有該鎖的程序都釋放該鎖后,才能關(guān)閉radio功能。
frameworks/base/services/java/com/android/server/WifiService.java
private final WifiStateTracker mWifiStateTracker;
private Context mContext;
private WifiWatchdogService mWifiWatchdogService = null;
private final
這是WifiService中的幾個(gè)重要的數(shù)據(jù)成員。
在接下來的構(gòu)造函數(shù)中初始化了mWifiStateTracker,mContext,然后動(dòng)態(tài)生成mWifiThread子線程并啟動(dòng),在主線程里用mWifiThread調(diào)用getLooper()函數(shù)獲得線程的looper,來初始化創(chuàng)建一個(gè)mWifiHandler對(duì)象,這個(gè)WifiHandler在WifiService類的后面有定義,并重載了Handler類的handlermessage()函數(shù),這樣消息就可以在主線程里被處理了,這是android的handlerthread消息處理機(jī)制,可參考相關(guān)資料,這里不予詳述。在構(gòu)造函數(shù)的最后,注冊(cè)了兩個(gè)廣播接收器,分別用來ACTION_AIRPLANE_MODE_CHANGED和ACTION_TETHER_STATE_CHANGED這兩個(gè)動(dòng)作,這里是android的intent消息通知機(jī)制,請(qǐng)參考相關(guān)資料,代碼如下:
mContext = context;
mWifiStateTracker = tracker;
mWifiStateTracker.enableRssiPolling(true);
……
HandlerThread wifiThread = new HandlerThread("WifiService");
wifiThread.start();
mWifiHandler = new WifiHandler(wifiThread.getLooper());
……
隨后定義了一系列的函數(shù),其中有服務(wù)器要發(fā)送的命令的系列函數(shù),它通過mWifiStateTracker成員類調(diào)用自己的的發(fā)送命令的接口(其實(shí)就是對(duì)本地接口的一個(gè)封裝),最后通過適配層發(fā)送命令給wpa_supplicant,而事件處理只到WifiStateTracker層被處理。
要注意的是,在WifiService中,定義了一些函數(shù)來創(chuàng)建消息,并通過mWifiHandler將消息發(fā)送到消息隊(duì)列上,然后在mHandlerThread線程體run()分發(fā)\處理消息,在主線程中被mWifiHandler的handlerMessage()函數(shù)處理,最后調(diào)用mWifiStateTracker的對(duì)應(yīng)函數(shù)來實(shí)現(xiàn)的。這里我也不明白為什么WifiService不直接調(diào)用mWifiStateTracker對(duì)應(yīng)的函數(shù),還要通過消息處理機(jī)制,繞了一圈在調(diào)用,當(dāng)然Google這么做肯定是有它道理的,忘高手指點(diǎn)。
frameworks/base/wifi/java/android/net/wifi/WifiStateTracker.java
NetworkStateTracker繼承了handler類,而WifiStateTracker繼承了NetworkStateTracker類,就是說WifiStateTracker間接繼承了handler類,屬于一個(gè)事件處理類。
WifiStateTracker類首先定義了事件日志和事件碼(這里包含了所有可能的事件類型),還定義了如下的重要成員數(shù)據(jù):
private WifiMonitor mWifiMonitor;
private WifiInfo mWifiInfo;
private WifiManager mWM;
private DhcpHandler mDhcpTarget;
private DhcpInfo mDhcpInfo;
類的構(gòu)造函數(shù)中,初始化了系列成員變量,包括生成了WifiMonitor的實(shí)例,在構(gòu)造函數(shù)中,因?yàn)?/span>WifiStateTracker是一個(gè)handler間接子類,所以他會(huì)自動(dòng)調(diào)用handler的無參構(gòu)造函數(shù),獲得looper和Queue消息隊(duì)列。
然后定義了一些設(shè)置supplicant和更新網(wǎng)絡(luò)信息的輔助函數(shù)。
這里也定義了很多的WfiNative接口函數(shù),這是JNI的本地接口;類DhcpHandler extends Handler{}也是在該類中定義的,它也是一個(gè)handler的子類,用來處理DHCP相關(guān)的消息EVENT_DHCP_START,可以想到它和WifiStateTracker不是共用一個(gè)looper。
聲明了一個(gè)重要的成員變量:mWifiStateTracker,并在構(gòu)造函數(shù)中由參數(shù)提供初始化,還定義了一系列的可能從wpa_supplicant層接收的事件類型及其名字,這些是消息處理機(jī)制的基礎(chǔ)。
startMonitoring()函數(shù),這是一個(gè)線程啟動(dòng)的封裝函數(shù),WifiStateTracker就是通過這個(gè)函數(shù)啟動(dòng)的WifiThread。
這個(gè)重要的類classMonitorThread extends Thread{};它是一個(gè)監(jiān)控進(jìn)程類,里面有一系列的事件處理函數(shù)和一個(gè)重要的Run()函數(shù),run函數(shù)主要流程:connectToSupplicant()連接精靈進(jìn)程wpa_supplicant,這里有一個(gè)mWifiStateTracker.notifySupplicantXXX()的調(diào)用,通知上層是否連接成功,然后就是一個(gè)輪詢過程,其中調(diào)用了WifiNative.waitForEvent()本地輪詢函數(shù)接口,并從返回的事件字符串類型中提取事件的名稱,最后通過事件的名稱調(diào)用相應(yīng)的事件處理函數(shù),并將事件轉(zhuǎn)換成mWifiStateTracker能識(shí)別的類型上報(bào)。
里面定義了一個(gè)類WifiNative:其中聲明了許多本地接口,可由native的標(biāo)志看出,這是Java代碼和本地庫之間的聯(lián)系接口;
frameworks/base/core/jni/
一類是命令相關(guān)的(控制)函數(shù),就是在JNI層android_XXX_Command()函數(shù)所調(diào)用的::Wifi_Command()函數(shù),調(diào)用流程:android_XXX_command()=>docommand()=>wifi_command()=>wifi_send_command()=>wpa_ctrl_require()。
二類是監(jiān)聽函數(shù),即Wifi_wait_for_event()函數(shù),調(diào)用流程:android_net_wifi_Waitforevent()=>wifi_wait_for_event()=>wpa_ctrl_recv()。
三類是剩下的函數(shù)。
10)wpa_supplicant與上層的接口,wpa_ctrl.c:external/wpa_supplicant
定義了三類套接字,并分別實(shí)現(xiàn)了和wpa_supplicant的通信,因此wpa_supplicant適配層和wpa_supplicant層是通過socket通訊的。
要是從wifi.c中真的很難看出它和wpa_supplicant有什么關(guān)系,和它聯(lián)系密切的是wpa_ctrl.h文件,這里面定義了一個(gè)類wpa_ctrl,這個(gè)類中聲明了兩個(gè)Socket套接口,一個(gè)是本地一個(gè)是要連接的套接口,wpa_ctrl與wpa_supplicant的通信就需要socket來幫忙了,而wpa_supplicant就是通過調(diào)用wpa_ctrl.h中定義的函數(shù)和wpa_supplicant進(jìn)行通訊的,wpa_ctrl類(其實(shí)是其中的兩個(gè)socket)就是他們之間的橋梁。
首先聲明了兩個(gè)主要變量mWifiStateTracker,mWifiManager,需要這兩個(gè)類對(duì)象來完成具體的控制工作,在WifiWatchdogService的構(gòu)造函數(shù)中,創(chuàng)建了這兩個(gè)類,并通過regesterForWifiBroadcast
frameworks/base/services/java/com/android/server/WifiWatchdogService.java
WifiWatchdogService(Context context, WifiStateTracker wifiStateTracker) {
聯(lián)系客服