7.       Ad hoc的支持

添加ad hoc的支持有两种方式,改wpa_supplicant和改Android Framework。 改wpa_supplicant的原理和方法请参考http://www.xda-developers.com/android/android-ad-hoc-wireless-network-support/, 这种方法不推荐, 不是解决问题的根本。下面是改Android Framework的方法。

在Android Framework中添加adhoc支持很简单, 可能只需要改一行代码(当然还没经过测试), 如下:

List<ScanResult> results = mWifiManager.getScanResults();

if (results != null) {

for (ScanResult result : results) {

// Ignore hidden and ad-hoc networks.

if (result.SSID == null || result.SSID.length() == 0 ||

result.capabilities.contains("[IBSS]")) {

continue;

}

boolean found = false;

for (AccessPoint accessPoint : accessPoints) {

if (accessPoint.update(result)) {

found = true;

}

}

if (!found) {

accessPoints.add(new AccessPoint(this, result));

}

}

}

上面一段代码在Settings应用的WifiSettings类里,发生在wpa_supplicant扫描ap结束时,将||result.capabilities.contains("[IBSS]")去掉即可支持adhoc。

可见google是故意禁了ad hoc的功能。 那么总有原因, 下面摘自某论坛:

What you say is true - it is relatively easy to support ad-hoc networks. I also appreciate that it sucks if you have to rely on ad-hoc wifi and you own an Android device.
However, there are good reasons as to why Android, or any OS for that matter, doesn't support it.

Ad-hoc networks are inherently insecure as they require no authentication for people joining the network. Ad-hoc networks were only ever intended to be used for very short term spontaneous and informal networks. "Short term", in this context, means the time it takes you to purchase a proper wireless access point.

Ad-hoc networks are highly discouraged, as not only are they insecure, but they interfere with people using the proper, secure, and recommended, infrastructure WiFi networks.

These facts probably demotivated Google from implementing support for it.

As most broadband (Cable or ADSL) routers come with WiFi these days, and as a lot of the rest of us (like me) use stand-alone wireless access points, the requirement for Ad-Hoc support is low. Also, as the phones that run Android have 3G, Edge, and GPRS support the need is even lower for Android users. As such, you can probably see why Google didn't bother - there are other features that more people "require", and so Google probably concentrated on adding those.

TODO: 怎样创建ad hoc网络让其它设备连进来?

8.       wifi direct

Wifi direct又叫wifi p2p, 是一种新型的技术, 用来取代蓝牙, 具有速度快连接方便的特点。 不过目前Android2.3还并不支持, 但应该会很快有支持。 下面是一些资料。

http://wireless.kernel.org/en/developers/p2p

Android4.0已经支持wifi direct api已经导出。

9.       Soft ap支持

软Ap可以为游戏应用提供联机对战的功能, 也可以基于软ap实现网络共享, 即连接到软Ap上的设备可以共享软Ap设备的网络, 比如手机可以作为软Ap, 笔记本连进来就可以通过手机的3g上网。

支持soft ap当然首先要驱动支持, 初步调研结论是ar6k驱动可以支持soft ap, 后续还需确认。

Android 2.2(froyo)开始支持soft ap, 可以在Settings程序里设置soft ap功能, 如下图:

但是我们在模拟器上并无上面的界面, 是在运行时会调用ConnectivityManager.isTetheringSupported()函数来判断系统是否支持Tethering, 如果不支持Tethering就隐藏上面界面。

开启Soft ap功能在Settings程序的WifiApEnabler. onPreferenceChange里, 设置soft ap在WifiApDialog.onClick里。它们依赖WifiManager的如下接口:

public boolean setWifiApEnabled(WifiConfiguration wifiConfig, booleanenabled)

public int getWifiApState()

public WifiConfiguration getWifiApConfiguration()

public boolean setWifiApConfiguration(WifiConfiguration wifiConfig)

WifiManager调用WifiService实现的功能, WifiService最终调用NetworkManagementService.startAccessPoint函数, 如下:

public void startAccessPoint(WifiConfiguration wifiConfig, String wlanIface, String softapIface)

throwsIllegalStateException {

mContext.enforceCallingOrSelfPermission(

android.Manifest.permission.CHANGE_NETWORK_STATE, "NetworkManagementService");

mContext.enforceCallingOrSelfPermission(

android.Manifest.permission.CHANGE_WIFI_STATE, "NetworkManagementService");

try {

mConnector.doCommand(String.format("softap stop " + wlanIface));

mConnector.doCommand(String.format("softap fwreload " + wlanIface + " AP"));

mConnector.doCommand(String.format("softap start " + wlanIface));

if (wifiConfig == null) {

mConnector.doCommand(String.format("softap set " + wlanIface + " " + softapIface));

else {

String str = String.format("softap set " + wlanIface + " " + softapIface +

" %s %s %s", convertQuotedString(wifiConfig.SSID),

wifiConfig.allowedKeyManagement.get(KeyMgmt.WPA_PSK) ?

"wpa2-psk" : "open",

convertQuotedString(wifiConfig.preSharedKey));

mConnector.doCommand(str);

}

mConnector.doCommand(String.format("softap startap"));

catch (NativeDaemonConnectorException e) {

throw new IllegalStateException("Error communicating to native daemon to start softap", e);

}

}

NetworkManagementService顾名思义是Android系统的网络管理服务, 负责比较特殊的网络的设置(比如网络共享(Tether)和网络地址转换(Nat)和ip 转发(ip forwording))和向上层通知网络相关的事件。mConnector是一个NativeDaemonConnector, 这里用来和系统的netd守护进程通信。NetworkManagementService的好多功能都是通过Netd实现的。 Netd的代码在“android sources”/system/netd里。Netd中softap控制的功能在“android sources”/system/netd/SoftapController.{h,cpp}里, 是通过wireless extention定义的SIOCGIWPRIV来调用网卡驱动的ap功能。 如果具体网卡驱动提供的soft ap接口不同, SoftapController的代码就需要改。比如ar6k的驱动厂家提供了hostapd来控制ap, 就需要改SoftapController来适配hostapd提供的接口。

10.   Wifi Tethering支持

在Settings程序里看不到关于Wifi Tethering的任何代码, 着实让我迷惑了一下。 原来开启soft ap功能后就会自动启动wifi tethering。 com.android.server.connectivity.Tethering类向NetworkManagementService(NetworkManagementService通过netd来监听, netd用netlink socket监听内核热插拔事件)类注册了一个Observer来监听Interface的add, remove, change的信息。 当使能soft ap时, 会以soft ap模式加载驱动, 此时驱动会发出热插拔事件。 Tethering类里面跑了两种状态机, 一个TetherMasterSM, 和n个TetherInterfaceSM(每个tetherable interface对应一个)。 添加Interface时就会启动一个TetherInterfaceSM状态机, 并进入Initial状态, 发出ConnectivityManager.ACTION_TETHER_STATE_CHANGED广播。 WifiService收到广播后调用ConnectivityService.tethering(inf)函数, 给TetherInterfaceSM发送CMD_TETHER_REQUESTED命令, 进入tethered状态。

当UpstreamIface(比如现在不共享以太网而变为共享3g网络)发生变化时, TetherMasterSM会通知所有TetherInterfaceSM改变nat。

TetherMasterSM初始阶段UpstreamIface的选择是根据从NetworkManagementServicem获得所有Ingerface,能匹配上com.android.internal.R.array.config_tether_upstream_regexs(在base.core.res.res.values.configs中定义, 原始为空需要根据实际情况来改)的第一个状态为up的interface即被选为UpstreamIface。

运行时UpstreamIface也可能变化, Tethering类监听ConnectivityManager.CONNECTIVITY_ACTION事件(当网络连接变化时由ConnectivityService发出), 当收到时给TetherMasterSM发TetherMasterSM.CMD_UPSTREAM_CHANGED消息。 TetherMasterSM收到后重新选择UpstreamIface,并向所有TetherInterfaceSM发送TetherInterfaceSM.CMD_TETHER_CONNECTION_CHANGED事件来用新的UpstreamIface重启Nat。

Tethering原理如下:

NetworkManagementService.setIpForwardingEnabled(true)

NetworkManagementService.startTethering(mDhcpRange)// 启动dnsmasq(负责dhcp和dns forwarding)

NetworkManagementService. setDnsForwarders(mDnsServers)//通过给dnsmasq发命令来设置dns服务器

NetworkManagementService.enableNat(String internalInterface, String externalInterface)//启动nat(网络地址转换)

11.   Usb Tethering支持

何谓usb tethering, 这里举个例子, 我们的设备连上了wifi, 此时将设备通过usb连接到pc, pc即可以共享我们设备的wifi网络, 可以将我们的设备看做是一块usb接口的无线网卡。

Wifi Tethering从用户的角度来看是手动启动(通过Settings使能soft ap), 但从原理上看是自动启动, 使能soft ap后NetworkManagementService收到interfaceAdded信号后便自动启动wifi tethering。

而usb tethering则不同, 无论从用户的角度还是从原理的角度都是手动启动。 当设备通过usb连上pc时,NetworkManagementService会收到interfaceAdded信号。 不过并不能立刻开启tethering, 因为连上pc的目的并不只有一个, 用户想要的可能是读写设备的sd卡。所以Usb Tethering会很关心Usb.ACTION_USB_STATE,Intent.ACTION_MEDIA_SHARED和Intent.ACTION_MEDIA_UNSHARED事件。 只有当usb连上并且media unshared的情况下才可以usb tethering。 在tethering过程中收到Intent.ACTION_MEDIA_SHARED, Tethering类和WifiSettings类都会有相应的动作。

手动在Settings里启动UsbTethering时, 会调用ConnectivityService.Tethering(inf)函数开启usb tethering。

原理如下:

NetworkManagementService.setIpForwardingEn cpRange)// 启动dnsmasq(负责dhcp和dns forwarding)

NetworkManagementService.setDnsForwarders(mDnsServers)//通过给dnsmasq发命令来设置dns服务器

Tethering.configureUsbIface(true)//配置usb interface: ip, netmask, up

Tethering.enableUsbRndis(true)//开启Usb Rndis(Remote Network Driver Interface Specification),使设备变成usb无线网卡

NetworkManagementService.enableNat(String internalInterface, String externalInterface)//启动nat(网络地址转换)abled(true)

NetworkManagementService.startTethering(mDh

另外补充一点,如果是Windows还需要安装usb tethering驱动才可以: http://www.android.com/tether。

12.   Reverse usb Tethering

何谓Reverse usb Tethering?usb Tethering让pc可以通过我们的设备上网,  Reverse usb Tethering是设备可以通过Pc上网, 只要usb线连上pc。

目前Android不支持, Framework只改Settings程序应该就可以添加支持, 在驱动层也需要支持, 可能只是编译内核时打开某些选项而已, 待确定。

未完待续……

13.   Ethernet Tethering

所谓Ethernet Tethering, 即Pc机通过网线连接到设备时即可共享设备的wifi或3g网络。

目前Android不支持,有线网卡connected后3g和wifi都会禁掉。

14.   需要改动的地方

针对5201平台(ar6k驱动), 我们需要对framework做如下修改。

基本:

“android sources”\hardware\libhardware_legacy\wifi\wifi.c:驱动名称

l         Adhoc支持:

Settings应用的WifiSettings类:将隐藏adhoc网络的代码去掉

l         Softap支持:

“android sources”/system/netd/SoftapController.{h,cpp}:适配到hostapd

“android sources”\hardware\libhardware_legacy\wifi\wifi.c:驱动的参数决定模式(ap or station)

com.android.server.connectivity: ip, default dns

l         Wifi Tethering支持:

base.core.res.res.values.configs: 根据平台实际情况修改config_tether_upstream_regexs,array.config_tether_wifi_regexs,  array.config_tether_usb_regexs。

l         Usb Tethering支持:

base.core.res.res.values.configs:根据平台实际情况修改array.config_tether_usb_regexs。

15.   测试

驱动的测试可以借助工具比如wpa_cli。 当我们改好framework代码后, 怎样确保它能工作呢?Android framework针对ConnectivityManager和WifiManager的单元测试,位于core.test.ConnectivityManagerTest中,  都是依赖于真实硬件的, 模拟器做不了。 当我们改了代码后, 可以运行这些单元测试来确保我们的改动。

运行WifiConnectionTest命令:

adb shell am instrument -e class  \

com.android.connectivitymanagertest.functional.WifiConnectionTest  \

-w com.android.connectivitymanagertest/.ConnectivityManagerTestRunner

运行WifiSoftAPTest命令:

adb shell am instrument \

-w com.android.connectivitymanagertest/.ConnectivityManagerUnitTestRunner

详情看代码。

16.   调试中遇到的问题

系统中多个Dhcpcd进程存在, 经查是setproperty(“ctl.stop”, “dhcpcd_eth0”)不能停掉Dhcpcd进程, 以至于下次启动时又会创建新的Dhcpcd进程。 最后发现是启动dhcp参数问题导致,应用-B参数不让dpcp以daemon形式运行即可。

android 2.3 wifi (二)相关推荐

  1. 【Android】多功能二维码实现思路,自动连接WI-FI

    现在项目的需求是: 1. 带AP功能的机顶盒端能生成二维码,供手机客户端扫描 1.1 如果用非特定应用(手机助手)扫描,则跳转下载手机助手界面 1.2 如果用手机助手扫描,自动连接到该机顶盒的WI-F ...

  2. Android手机通过wifi进行数据传输(二)

    上文接 Android手机通过wifi进行数据传输(一) 本文参照自: [Android连接Wifi和创建Wifi热点 demo] 以下是源码文件 原文件Constant.java package e ...

  3. android usb wifi驱动下载,android 平台USB wifi驱动移植及使用

    一.   Android平台Wifi的基本代码路径 1.       Wpa_supplicant源码部分 external/wpa_supplicant_6/ 生成库libwpa_client.so ...

  4. 最简单DIY基于ESP8266的智能彩灯⑥(Android开发通过WIFI控制彩灯实现表白神器)

    ESP8266和ESP32智能彩灯开发系列文章目录 第一篇:最简单DIY基于ESP8266的智能彩灯①(在网页用按钮点亮普通RGB灯) 第二篇:最简单DIY基于ESP8266的智能彩灯②(在网页用按键 ...

  5. (一百九十六)Android Q 学习WiFi的评分机制(三)

    前言:之前在(一百九十六)Android Q 学习WiFi的评分机制(二)梳理了CS对WiFi score变化的处理,主要是rematchAllNetworksAndRequests方法中的处理,其中 ...

  6. Android bluetooth介绍(二): android 蓝牙代码架构及其uart 到rfcomm流程

    关键词:蓝牙blueZ  UART  HCI_UART H4  HCI  L2CAP RFCOMM  版本:基于android4.2之前版本 bluez内核:linux/linux3.08 系统:an ...

  7. Android Studio 使用 WIFI 连接手机

    Android Studio 使用 WIFI 连接手机 手机连线经常接触不良, 连上又断又连上又断的时候, 只要确保有一点时间让你连上 adb wifi, 就不用再听到那烦人的声音. 注意手机跟电脑必 ...

  8. 深入Android系统(十二)Android图形显示系统-2-SurfaceFlinger与图像输出

    最近有些忙,切实体验了一把拖更的羞耻感 ( *︾▽︾) 本文和上一篇深入Android系统(十二)Android图形显示系统-1-显示原理与Surface关系比较密切,撸完前篇更易理解本文啦 (๑‾ ...

  9. Android 天气APP(二十六)增加自动更新(检查版本、通知栏下载、自动安装)

    上一篇:Android 天气APP(二十五)地图天气(下)嵌套滑动布局渲染天气数据 效果图 开发流程 1.开发前言 2.上传应用到分发平台 3.版本数据请求与存储 4.检查版本更新.自定义更新提示弹窗 ...

  10. Android Stuido 使用WIFI测试

    Android Studio 使用WIFI测试 前置准备 操作步骤 连接方式 1.通过USB线连接 2.通过ADB连接 当使用Android Studio进行真机测试时,需要数据线进行连接 那么如何使 ...

最新文章

  1. 【控制】李亚普诺夫稳定性分析
  2. 【Python教程】七种创建对象的方式,你知道几种?
  3. [USACO1.3]牛式 Prime Cryptarithm
  4. textFiled输入字数的控制问题之—把带输入的拼音也判断了
  5. 使用prismjs为网站添加代码高亮功能
  6. uniapp滑动切换tab标签_Web前端,Tab切换,缓存,页面处理的几种方式
  7. Verilog实现2分频实例
  8. angular6 设置全局变量_angularjs 设置全局变量的3种方法
  9. active mq topic消费后删除_RabbitMQ重复消费,顺序消费,消息丢失如何解决
  10. Python技术公众号100天了
  11. 酒店客房卫生打扫步骤及重点
  12. 计算机自检报错无法开机,BIOS维修网站www.biosrepair.com-开机自检BIOS错误代码解析...
  13. 2021年全新大数据学习路线图,(含入门到精通项目学习免费教程哦)
  14. Mybatis实现逆向工程
  15. pandas daraframe 写入读取excel文件,并简单计算
  16. 【合规性检查方法-Fitness 2】基于Alignment的拟合度评估方法
  17. 一场胆战心惊的B站面试,哔哩哔哩也太难进了
  18. office修复找不到msi_office2013安装出错,老是出现找不到officeMUI.msi或则officeMUI.xml等,是什么原 - Microsoft Community...
  19. python tell_Python 文件 tell() 使用方法及示例
  20. 分布式技术一周技术动态 2015.12.13

热门文章

  1. ORA_ERROR大全
  2. 9.1 爬虫及爬行方式
  3. 想提高程序员的思维深度?这6本书你就不得不读
  4. 提供一个免费的CSDN下载账号
  5. FormData+Ajax文件上传
  6. 一斤鸡蛋一毛钱?一个月卖了100多万,95后小姑娘的连环方案!
  7. 2021年新西兰经济发展研究报告
  8. 音频压缩编码技术(五)—ffmpeg命令方式生成AAC文件
  9. 35岁被称为中年男人,失业之后可以做些什么
  10. Python笔记(1-20)