




已阅读5页,还剩79页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1 WIFI 学习总结学习总结 1WLAN 技术.3 2802.11 协议简述.3 2.1.1概述.3 3802.11 四种主要物理组件.4 3.1工作站(Station).4 3.2接入点(Access Point).4 3.3无线媒介(Wireless Medium).4 3.4分布式系统(Distribution System).4 4WIFI 适配层.5 5wpa_supplicant.6 5.1wpa_ctrl 的作用.6 5.2WPA_SUPPLICANT.6 5.2.1概念.6 5.2.2Wpa_supplicant 与驱动的交互.6 6Wpa_cli 调试工具.7 6.1启动 wpa_supplicant. 7 6.2连接 wpa_cli 到 wpa_supplicant.7 6.3示例.8 6.3.1无密钥认证 AP. 8 6.3.2WEP 认证 AP.8 6.3.3WPA-PSK/WPA2-PSK 认证 AP.8 6.3.4隐藏 AP. 9 7Wifi 模块解析和启动流程. 9 7.1框架分析.9 7.2Wifi 启动流程.11 8WLAN 驱动结构介绍.22 8.1SDIO 驱动. 22 8.2Boardcom 无线通讯芯片.23 8.2.1概述.23 8.2.2源码.23 8.3详细接口及代码分析. 24 8.3.1WIFI 驱动流程分析.24 8.3.2WIFI 设备注册流程.25 8.3.3WIFI 驱动流程(二).40 8.3.4网络设备注册流程. 43 9IOCTL 的调用逻辑.48 10数据的传送.56 10.1数据传送过程简述. 56 10.2Bcm4329 芯片 wlan 驱动数据传送.57 10.3传输超时.59 2 11数据的接收.59 11.1数据接收的方式和过程. 59 11.2选择哪种接收模式.60 11.3Bcm4329 芯片 wlan 驱动数据传送.60 12电源管理相关的调用逻辑. 65 13Android 平台的 Wifi 模块移植要点.74 13.1Wifi 结构.74 13.2Wifi 模块环境. 75 13.3Wifi 模块的编译. 75 13.3.1Wifi 驱动源码. 75 13.3.2在 android 平台添加 BCM43xx 驱动.75 13.3.3编译 wifi 驱动源码.79 13.3.4在 android 中使用 BCM43xx.80 3 1WLAN 技术技术 WLAN 是英文 WirelessLAN 的缩写,就是无线局域网的意思。无线以太网 技术是一种基于无线传输的局域网技术,与有线网络技术相比,具有灵活、建网 迅速、个人化等特点。将这一技术应用于电信网的接入网领域,能够方便、灵活 地为用户提供网络接入,适合于用户流动性较大、有数据业务需求的公共场所、 高端的企业及家庭用户、 需要临时建网的场合以及难以采用有线接入方式的环境 等。 2802.11 协议简述协议简述 2.1.1 概述概述 作为全球公认的局域网权威, IEEE802 工作组建立的标准在过去二十年内在 局域网领域独领风骚。 这些协议包括了 802.3Ethernet 协议、 802.5TokenRing 协议、 802.3z100BASET 快速以太网协议。 在 1997 年, 经过了 7 年的工作以后, IEEE 发布了 802.11 协议,这也是在无线局域网领域内的第一个国际上被认可的协议。 在 1999 年 9 月,他们又提出了 802.11bHighRate协议,用来对 802.11 协议 进行补充,802.11b 在 802.11 的 1Mbps 和 2Mbps 速率下又增加了 5.5Mbps 和 11Mbps 两个新的网络吞吐速率。利用 802.11b,移动用户能够获得同 Ethernet 一 样的性能、网络吞吐率、可用性。这个基于标准的技术使得管理员可以根据环境 选择合适的局域网技术来构造自己的网络, 满足他们的商业用户和其他用户的需 求。 802.11 协议主要工作在 ISO 协议的最低两层上, 并在物理层上进行了一些改 动,加入了高速数字传输的特性和连接的稳定性。 主要内容: 1.802.11 工作方式 2.802.11 物理层 3.802.11b 的增强物理层 4.802.11 数字链路层 5.联合结构、蜂窝结构和漫游 4 3802.11 四种主要物理组件四种主要物理组件 3.1 工作站(工作站(Station) 构建网络的主要目的是为了在工作站间传送数据。所谓工作站,是指配备无 线网络接口的计算设备。 3.2 接入点(接入点(Access Point) 802.11 网络所使用的帧必须经过转换,方能被传递至其他不同类型的网络。 具备无线至有线的桥接功能的设备称为接入点,接入点的功能不仅于此,但桥接 最为重要。 3.3 无线媒介(无线媒介(Wireless Medium) 802.11 标准以无线媒介在工作站之间传递帧。其所定义的物理层不只是一 种,802.11 最初标准化了两种射频物理层以及一种红外线物理层。 3.4 分布式系统(分布式系统(Distribution System) 当几个接入点串联以覆盖较大区域时, 彼此之间必须相互通信以掌握移动式 工作站的行踪。分布式系统属于 802.11 的逻辑组件,负责将帧转送至目的地。 下图为 802.11 网络的基本服务集(basic service set) ,其中包含了这四种物 理组件。 5 4WIFI 适配层 里面定义很多字符串变量和适配层的接口实现,是对 wpa_supplicant 程序通 信 的 接 口 封 装 , 用 来 完 成 上 层 和 wpa_supplicant 的 通 信 ,头 文 件 在 libhardware/include/hardware 下,这里的函数用来向 JNI 的本地实现提供调用接 口。 这里的函数,我把它们分为四类函数: 一类是命令相关的(控制)函数,就是在 JNI 层 android_XXX_Command() 函数所调用 的 Wifi_Command()函数,调用流程如下: android_XXX_command()=docommand()=wifi_command()=wifi_send_co mmand()=wpa_ctrl_require()。 二类是监听函数,即 Wifi_wait_for_event()函数,调用流程如下 : android_net_wifi_Waitforevent()= wifi_wait_for_event()=wpa_ctrl_recv()。 三就是 WPA_SUPPLICANT 的启动,连接,关闭函数 四是驱动的加载和卸载函数 6 5wpa_supplicant 5.1 wpa_ctrl 的作用的作用 定义了两类套接字和一个管道,并分别实现了和 wpa_supplicant 的通信,而 在实际的实现中采用的都是套接字的方式,因此 wpa_supplicant 适配层和 wpa_supplicant 层 是通过 socket 通讯的。 要是从 wifi.c 中真的很难看出它和 wpa_supplicant 有什么关系,和它联系密 切的就是 这个 wpa_ctrl.h 文件,这里面定义了一个类 wpa_ctrl,这个类中声明了 两个 Socket 套接口,一个是本地一个是要连接的套接口,wpa_ctrl 与 wpa_supplicant 的通信就需要 socket 来帮忙了,而 wpa_supplicant 就是通过调用 wpa_ctrl.h 中定义的函数和 wpa_supplicant 进行通讯的,wpa_ctrl 类(其实是其中 的两个 socket)就是他们之间的桥梁。 5.2 WPA_SUPPLICANT 5.2.1 概念概念 wpa_supplicant 本是开源项目源码,被谷歌修改后加入 android 移动平台, 它 主要是用来支持 WEP,WPA/WPA2 和 WAPI 无线协议和加密认证的,而实际上 的工作内容是通过 socket(不管是 wpa_supplicant 与上层还是 wpa_supplicant 与 驱动都采用 socket 通讯)与驱动交互上报数据给用户,而用户可以通过 socket 发送命令给 wpa_supplicant 调动驱动来对 WiFi 芯片操作。简单的说, wpa_supplicant 就是 WiFi 驱动和用户的中转站外加对协议和加密认证的支持。 5.2.2 Wpa_supplicant 与驱动的交互与驱动的交互 5.2.2.1wpa_supplicant.c 首 先 定 义 一 个 驱 动 操 作 数 组externstructwpa_driver_ops *wpa_supplicant_drivers,然后是系列 wpa_supplicant_XXX()函数,很多函数里 面调用 wpa_drv_XXX()函数,这些函数是 wpa_supplicant_i.h 中实现的函数。几 乎每个函数都需要一个 wpa_supplicant 结 构,对其进行所有的控制和通信操作。 5.2.2.2Wpa_supplicant_i.h 其中定义了一个重要数据结构 wpa_supplicant,其中有一个重要的 driver 成 7 员,它是 wpa_driver_ops 类型,可以被用来调用抽象层的接口。接下来是系列函 数声明,这些函数声明在 wpa_supplicant.c 中实现,然后就是 wpa_drv_XXX 函 数,这些函数就是在 wpa_supplicant.c 中被 wpa_supplicant_xxx 函数调用的,而 这些 wpa_drv_xxx 函数也都有一个 wpa_supplicant 结构的变量指针, 用来调用封 装的抽象接口,而这些抽象接口的实现在 driver_wext.c 中(如果使用的汉斯 WEXT 驱动) 。 这里要注意的是: 在 wpa_suppliant.c 文件中定义的很多函数是在该头文件中 声明的,而不是在 wpa_supplicant.h 中声明的。 5.2.2.3Driver_wext.c 对 wpa_drvier_ops 的个函数的具体实现,该结构指针在 wpa_supplicant 注册 一个网络接口时会被初始化赋予指定的操作指针,wpa_supplicant.c 中的 wpa_supplicant_xxx 函数通过 wpa_supplicant 结构中的该操作指针调用 WEXT 的 实现接口。 就是在该文件中,创建了三个 socket:ioctrl_socket,event_socket 和 mlme_socket,它们分别有自己的用途,如 ioctrl_socket 用于发送控制命令, event_socket用于监听驱动传来的event事件等。 Wpa_supplicant通过这三个socket 与 wifi 驱动关联,这里的 socket 同 fd(文件描述符)类似。 6Wpa_cli 调试工具调试工具 6.1 启动启动 wpa_supplicant 使用下面命令启动 wpa_supplicant: wpa_supplicant-Dwext-iwlan0-C/data/system/wpa_supplicant -c/data/misc/wifi/wpa_supplicant.conf 为了确保 wpa_supplicant 真的启动起来了,使用“ps”命令查看。 6.2连接连接 wpa_cli 到到 wpa_supplicant wpa_cli -p/data/system/wpa_supplicant -iwlan0 然后,就可以使用 wpa_cli 调试工具进行 wifi 调试了,下面列出了一些 常用的调试命令: 8 scan/扫描周围的 AP scan_results/显示扫描结果 status/显示当前的连接状态信息 terminate/终止 wpa_supplicant quit/退出 wpa_cli add_network/返回可用 network id set_network /设置网络 select_network /选择网络,禁用其它网络 disable_network /禁用网络 enable_network /启用网络 6.3 示例示例 6.3.1 无密钥认证无密钥认证 AP add_network(返回可用 network id, 假定返回 0) set_network 0 ssid “666” set_network 0 key_mgmt NONE enable_network 0 quit 如果上面的操作正确,我们会连接到一个 AP,它的 SSID 为“666” ,现在 需要一个 IP 来访问 internet: dhcpcd wlan0 成功获取 IP 后,即可连上 internet。 6.3.2 WEP 认证认证 AP add_network(假设返回 1) set_network 1 ssid “666” set_network 1 key_mgmt NONE set_network 1 wep_key0 “ap passwork” set_network 1 wep_tx_keyidx 0 select_network 1(如果你已经连上了其它的 AP,那么就需要这 个命令来禁用其它的网络) enable_network 1 然后同上获取 IP,连接到 internet 上。 6.3.3 WPA-PSK/WPA2-PSK 认证认证 AP add_network(假定返回 2) set_network 2 ssid “666” set_network 2 psk “your pre-shared key” 9 select_network 2 enable_network 2 还有其它的命令进一步设置网络,不过 wpa_supplicant 已经给了我们一些默 认的配置。 6.3.4隐藏隐藏 AP 原则上应该只要在上面的基础上去 set_network netid scan_ssid 1 即可, 测试 过无加密的 Hidden AP,WEP/WPA/WPA2 应该道理一样。 7Wifi 模块解析和启动流程 7.1 框架分析框架分析 WIFI 整体框架如图所示: 10 WirelessSettings WifiSettingAccessPointDialog WifiEnablerWifiLayer WifiManagerWifiStateTracker Wifi Wpa_supplicant Kernel/net驱动 Wifi电源管理驱动 WiFi模块驱动.ko Wifi模组 WifiServiceWifiMonitor WifiNatvie Android_net_wifi_wifi WIFI_STATE_CHANGED_ACTION NETWORK_STATE_CHANGED_AC TION SCAN_RESULTS_AVAILABLE_AC TION JAVAVM 首先,用户程序使用 WifiManager 类来管理 Wifi 模块,它能够获得 Wifi 模 11 块的状态,配置和控制 Wifi 模块,而所有这些操作都要依赖 Wifiservice 类来实 现。 WifiService 和 WifiMonitor 类是 Wifi 框架的核心,如图所示。下面先来看 看 WifiService 是什么时候,怎么被创建和初始化 的。 在 systemServer 启动之后,它会创建一个 ConnectivityServer 对象,这个对 象的构造函数会创建一个 WifiService 的实例,代码如下所示: framework/base/services/java/com/android/server/ConnectivityService.java case ConnectivityManager.TYPE_WIFI: if (DBG) Slog.v(TAG, Starting Wifi Service.); WifiStateTrackerwst=newWifiStateTracker(context, mHandler);/创建 WifiStateTracker 实例 WifiService wifiService = newWifiService(context, wst);/创建创建 WifiService 实实 例例 ServiceManager.addService(Context.WIFI_SERVICE, wifiService);/向服 务管理系统添加 Wifi 服务 wifiService.startWifi();/启动 Wifi mNetTrackersConnectivityManager.TYPE_WIFI = wst; wst.startMonitoring(); /启动 WifiMonitor 中的 WifiThread 线程 WifiService 的主要工作:WifiMonitor 和 Wpa_supplicant 的启动和关闭, 向 Wpa_supplicant 发送命令。 WifiMonitor 的主要工作:阻塞监听并接收来自 Wpa_supplicant 的消息, 然后发送给 WifiStateTracker。 上面两个线程通过 AF_UNIX 套接字和 Wpa_supplicant 通信,在通信过 程中有两种连接方式:控制连接和监听连接。它们创建代码如下: ctrl_conn =wpa_ctrl_open(ifname); . . . monitor_conn = wpa_ctrl_open(ifname); 7.2 Wifi 启动流程启动流程 (1)使能 Wifi 要想使用 Wifi 模块,必须首先使能 Wifi,当你第一次按下 Wifi 使能按 12 钮时,WirelessSettings 会实例化一个 WifiEnabler 对象,实例化代码如下: packages/apps/settings/src/com/android/settings/WirelessSettings.java protected void onCreate(Bundle savedInstanceState) super.onCreate(savedInstanceState); CheckBoxPreferencewifi=(CheckBoxPreference) findPreference(KEY_TOGGLE_WIFI); mWifiEnabler= new WifiEnabler(this, wifi); WifiEnabler 类的定义大致如下,它实现了一个监听接口,当 WifiEnabler 对象被初始化后,它监听到你按键的动作,会调用响应函数 onPreferenceChange () ,这个函数会调用 WifiManager 的 setWifiEnabled()函数。 public class WifiEnabler implementsPreference.OnPreferenceChangeListener public boolean onPreferenceChange(Preference preference,Object value) booleanenable = (Boolean) value; if (mWifiManager.setWifiEnabled(enable) mCheckBox.setEnabled(false); 我们都知道 Wifimanager 只是个服务代理,所以它会调用 WifiService 的 setWifiEnabled()函数,而这个函数会调用 sendEnableMessage()函数,了解 android 消 息 处 理 机 制 的 都 知 道 , 这 个 函 数 最 终 会 给 自 己 发 送 一 个 MESSAGE_ENABLE_WIFI 的消息,被 WifiService 里面定义的 handlermessage() 函数处理,会调用 setWifiEnabledBlocking()函数。下面是调用流程: mWifiEnabler.onpreferencechange()=mWifiManage.setWifienabled()=m WifiService.setWifiEnabled()=mWifiService.sendEnableMessage()=mWifiSer vice.handleMessage()=mWifiService.setWifiEnabledBlocking(). 在 setWifiEnabledBlocking()函数中主要做如下工作:加载 Wifi 驱动,启动 wpa_supplicant,注册广播接收器,启动 WifiThread 监听线程。代码如下: if (enable) if (!mWifiStateTracker.loadDriver() 13 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(); 至此,Wifi 使能结束,自动进入扫描阶段。 (2) 扫描 AP 当驱动加载成功后,如果配置文件的 AP_SCAN = 1,扫描会自动开始, WifiMonitor将会从supplicant收到一个消息 EVENT_DRIVER_STATE_CHANGED,调用 handleDriverEvent() ,然后调用 mWifiStateTracker.notifyDriverStarted() , 该 函 数 向 消 息 队 列添 加 EVENT_DRIVER_STATE_CHANGED,handlermessage()函数处理消息时调用 scan()函数,并通过 WifiNative 将扫描命令发送到 wpa_supplicant。 Frameworks/base/wifi/java/android/net/wifi/WifiMonitor.java private void handleDriverEvent(Stringstate) if (state = null) return; if (state.equals(STOPPED) mWifiStateTracker.notifyDriverStopped(); else if (state.equals(STARTED) mWifiStateTracker.notifyDriverStarted(); else if (state.equals(HANGED) mWifiStateTracker.notifyDriverHung(); Frameworks/base/wifi/java/android/net/wifi/WifiStateTracker.java case EVENT_DRIVER_STATE_CHANGED: switch(msg.arg1) case DRIVER_STARTED: 14 /* *Set the number of allowed radio channels according *to the system setting, since it gets reset by the *driver upon changing to the STARTED state. */ setNumAllowedChannels(); synchronized (this) if (mRunState = RUN_STATE_STARTING) mRunState = RUN_STATE_RUNNING; if (!mIsScanOnly) reconnectCommand(); else / In somesituations, supplicant needs to be kickstarted to / start thebackground scanning scan(true); break; 上面是启动 Wifi 时, 自动进行的 AP 的扫描, 用户当然也可以手动扫描 AP, 这部分实现在 WifiService 里面,WifiService 通过 startScan()接 口函数发送扫描 命令到 supplicant。 Frameworks/base/wifi/java/android/net/wifi/WifiStateTracker.java public boolean startScan(booleanforceActive) enforceChangePermission(); switch (mWifiStateTracker.getSupplicantState() case DISCONNECTED: case INACTIVE: case SCANNING: case DORMANT: break; default: mWifiStateTracker.setScanResultHandling( WifiStateTracker.SUPPL_SCAN_HANDLING_LIST_ONLY); break; return mWifiStateTracker.scan(forceActive); 然后下面的流程同上面的自动扫描,我们来分析一下手动扫描从哪里开 始的。 我们应该知道手动扫描是通过菜单键的扫描键来响应的,而响应该动作的 15 应该是 WifiSettings类中Scanner类的handlerMessage()函数, 它调用WifiManager 的 startScanActive(),这才调用 WifiService 的 startScan()。 packages/apps/Settings/src/com/android/settings/wifiwifisettings.java public boolean onCreateOptionsMenu(Menu menu) menu.add(Menu.NONE, MENU_ID_SCAN, 0, R.string.wifi_menu_scan) .setIcon(R.drawable.ic_menu_scan_network); menu.add(Menu.NONE, MENU_ID_ADVANCED, 0, R.string.wifi_menu_advanced) .setIcon(android.R.drawable.ic_menu_manage); return super.onCreateOptionsMenu(menu); 当按下菜单键时,WifiSettings 就会调用这个函数绘制菜单。如果选择扫 描按钮,WifiSettings 会调用 onOptionsItemSelected()。 packages/apps/Settings/src/com/android/settings/wifiwifisettings.java public booleanonOptionsItemSelected(MenuItem item) switch (item.getItemId() case MENU_ID_SCAN: if(mWifiManager.isWifiEnabled() mScanner.resume(); return true; case MENU_ID_ADVANCED: startActivity(new Intent(this,AdvancedSettings.class); return true; return super.onOptionsItemSelected(item); private class Scanner extends Handler private int mRetry = 0; void resume() if (!hasMessages(0) sendEmptyMessage(0); void pause() mRetry = 0; mAccessPoints.setProgress(false); removeMessages(0); 16 Override public void handleMessage(Message message) if (mWifiManager.startScanActive() mRetry = 0; else if (+mRetry = 3) mRetry = 0; Toast.makeText(WifiSettings.this, R.string.wifi_fail_to_scan, Toast.LENGTH_LONG).show(); return; mAccessPoints.setProgress(mRetry != 0); sendEmptyMessageDelayed(0, 6000); 这里的 mWifiManager.startScanActive()就会调用 WifiService 里 的 startScan ()函数,下面的流程和上面的一样,这里不赘述。 当 supplicant 完成了这个扫描命令后,它会发送一个消息给上 层,提醒他们 扫描已经完成,WifiMonitor 会接收到这消息,然后再发送给 WifiStateTracker。 Frameworks/base/wifi/java/android/net/wifi/WifiMonitor.java void handleEvent(int event, String remainder) switch (event) caseDISCONNECTED: handleNetworkStateChange(NetworkInfo.DetailedState.DISCONNECTED,remai nder); break; case CONNECTED: handleNetworkStateChange(NetworkInfo.DetailedState.CONNECTED,remainde r); break
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 脑机接口情绪调控策略-洞察及研究
- 渔业政策效果评价-洞察及研究
- 油墨厂耐戊苯试验细则
- 手抄报课件设置
- 四川省成都市浦江县2025-2026学年高一上学期第一次月考历史试题(含答案)
- 河南省郑州市新郑市2024-2025学年四年级下学期期末英语试题(含答案无听力原文无听力音频)
- 广西河池市2024-2025学年九年级上学期第一次月考化学试题(无答案)
- 手影变变变课件
- 印刷厂售后服务处理办法
- 学生自身安全培训计划课件
- 中药处方点评管理办法
- 国企纪法教育实施路径
- 药品发放登记管理制度
- 临床科室科研管理制度
- 铁艺围栏采购合同
- 中国皮肤基底细胞癌诊疗指南2023
- 卫星通信技术在电力行业中的应用场景分析
- 黄旭华人物介绍
- 《医疗机构工作人员廉洁从业九项准则》解读
- 教育行业重难点分析及解决措施
- 合伙开工厂 合同范例
评论
0/150
提交评论