打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
【Android】wifi热点项目总结

本文档基于Android 2.3.4,描述wifi热点相关工作事宜

 

1.     Android2.3.4设置里的便携式热点及相关配置显示出来。

<1>.配置android2.3.4\frameworks\base\core\res\res\values\Config.xml

 

增加相关tether interface:

<!-- caihua.zhao modify here 20120523 -->

<!-- List of regexpressions describing the interface (if any) that represent tetherable Wifi interfaces.  If the device doesn't want to support tethering over Wifi this should be empty.  An example would be "softap.*" -->

<string-array translatable="false" name="config_tether_wifi_regexs">

    <item>"wlan0"</item>

</string-array>

 

增加相关upstream interface: [增加的就是以太网的接口eth0]

<!-- Regex array of allowable upstream ifaces for tethering - for example if you want tethering on a new interface called "foo2" add <item>"foo\\d"</item> to the array -->

<string-array translatable="false" name="config_tether_upstream_regexs">

   <item>"eth0"</item>

</string-array>

 

<2>. 配置android2.3.4\device\softwinner\crane-common\ProductCommon.mk

增加:

PRODUCT_PROPERTY_OVERRIDES += ro.tether.denied=false

 

<3>.修改android2.3.4\frameworks\base\services\java\com\android\server\

ConnectivityService.java,接口函数ConnectivityService()

 

增加红色部分:

mTetheringConfigValid = (((mNetTrackers[ConnectivityManager.TYPE_MOBILE_DUN] != null)            ||(mNetTrackers[ConnectivityManager.TYPE_ETHERNET] != null)

||!mTethering.isDunRequired()) &&(mTethering.getTetherableUsbRegexs().length != 0 ||

mTethering.getTetherableWifiRegexs().length != 0) &&

mTethering.getUpstreamIfaceRegexs().length != 0);

 

上面三项修改后,重新编译后,在 android设置里就会找到便携式热点选项了!

 

 

 

 

2.     编译带ap功能的nano wifi driver(版本为7.0.8),从nanoradio原厂获得。

<1>.nano_7.0.8拷贝到linux wifi driver module目录:

    lichee\linux-2.6.36\modules\wifi\nano_7.0.8

<2>.配置build script,编译新的wifi driver.

修改lichee\linux-2.6.36\scripts\build_sun4i_crane.sh

    build_modules()  :

       #build swl-n20 sdio wifi module

    #make -C modules/wifi/nano-c047.12 LICHEE_MOD_DIR=${LICHEE_MOD_DIR} KERNEL_DIR=${LICHEE_KDIR} \

       #CONFIG_CHIP_ID=${CONFIG_CHIP_ID} HOST=${CROSS_COMPILE} INSTALL_DIR=${LICHEE_MOD_DIR} all install

    make -C modules/wifi/nano_7.0.8 LICHEE_MOD_DIR=${LICHEE_MOD_DIR} KERNEL_DIR=${LICHEE_KDIR} \

       CONFIG_CHIP_ID=${CONFIG_CHIP_ID} HOST=${CROSS_COMPILE} INSTALL_DIR=${LICHEE_MOD_DIR} all install

 

clean_modules() :

       #clean swl-n20 sdio wifi module

    #make -C modules/wifi/nano-c047.12 LICHEE_MOD_DIR=${LICHEE_MOD_DIR} KERNEL_DIR=${LICHEE_KDIR} \

       #CONFIG_CHIP_ID=${CONFIG_CHIP_ID} HOST=${CROSS_COMPILE} INSTALL_DIR=${LICHEE_MOD_DIR} clean

    make -C modules/wifi/nano_7.0.8 LICHEE_MOD_DIR=${LICHEE_MOD_DIR} KERNEL_DIR=${LICHEE_KDIR} \

CONFIG_CHIP_ID=${CONFIG_CHIP_ID} HOST=${CROSS_COMPILE} INSTALL_DIR=${LICHEE_MOD_DIR} clean

 

       这样的话,就可以编译新的wifi dirver了!

 

3.       修改wifi.c

    //caihua.zhao modify here

    //nano-c047.12      

    //#define WIFI_FIRMWARE_MODULE_ARG          "nrx_config=/drv"

    //nano_7.0.8

#define WIFI_FIRMWARE_MODULE_ARG          "nrx_fw_path=/drv/x_mac.axf"

其中x_mac.axfsoftap的固件fireware.

 

4.        编译,刷包后起机,android设置里欲启动wifi热点,不行,竟然出错,为什么呢?

    

查看debug知道: Exception in startAccessPoint() \ SIOCGIPRIV failed:

,同时知道wifi driverko及固件是成功加载的,而且也注册了wifi interface:wlan0

 

跟踪源码后知道引起这个问题有两个原因:

<1>.android2.3.4\frameworks\base\services\java\com\android\server\WifiService.java

private static final String SOFTAP_IFACE = "wl0.1"; 

需要修改为:

private static final String SOFTAP_IFACE = "wlan0";// "wl0.1"; 

<2>. android2.3.4\system\netd\ SoftapController.cpp

int SoftapController::getPrivFuncNum(char *iface, const char *fname) {

   ……

   if ((ret = ioctl(mSock, SIOCGIWPRIV, &wrq)) < 0) {

        LOGE("SIOCGIPRIV failed: %d", ret);

        return ret;

   }

   ……

}

 

   根据ioctl的流程,可以知道最终调用都wifi drivernanoiw.c:

 

static struct iw_handler_def nrx_iw_handler_def = {

   .standard = nrx_iw_handlers,

   .num_standard = ARRAY_SIZE(nrx_iw_handlers),

#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,33)

   || defined(CONFIG_WEXT_PRIV)

   .private = NULL,

   .num_private = 0,

   .private_args = NULL,

   .num_private_args = 0,

#endif

#if WIRELESS_EXT >= 17

   .get_wireless_stats = nrx_get_wireless_stats

#endif

};

#endif

由于没有定义相应的private接口函数,所以上述ioctl会出错。因为这个ioctl就是为了得到wifi driver定义的private函数接口地址。

 

问题点:

要想解决这个问题,必须在驱动里增加相应的接口函数。

nanoradio 技术支持说他也没有加过这样的接口,却没有提及其有开发的Android2.3.4SDK(坑爹哟!),后才知道这才是正道,我根据这个SDK大概花了不到两天时间,在android2.3.4softapclient都弄好了,或许是之前的折腾,让我熟悉很多工具和并对驱动也熟悉很多。另,也没有说,softapclient需要不同的固件,后来我们测试时,发现启动client功能时宕机,我查看流程在知道需要不同固件。

 

当时,我们商量先用命令行模式将softap调试好。

 

涉及到android系统中没有的命令有iwconfig hostapd

而已有命令如下:

iptablesdnsmasq.

命令简介:

iwconfigLinux Wireless Extensions(LWE)的用户层配置工具之一。LWELinux下对无线网络配置的工具,包括内核的支持、用户层配置工具和驱动接口的支持三部分。目前很多无线网卡都支持LWE,而且主流的Linux发布版本,比如Redhat LinuxUbuntu Linux都已经带了这个配置工具。

hostapd 是一个用户态用于AP和认证服务器的守护进程。它实现了IEEE 802.11相关的接入管理,IEEE 802.1X/WPA/WPA2/EAP 认证, RADIUS客户端,EAP服务器和RADIUS 认证服务器。Linux下支持的驱动有:Host APmadwifi,基于mac80211的驱动。

iptables IP 信息包过滤系统是一种功能强大的工具,可用于添加、编辑和除去规则,这些规则是在做信息包过滤决定时,防火墙所遵循和组成的规则。这些规则存储在专用的信息包过滤表中,而这些表集成在 Linux 内核中。在信息包过滤表中,规则被分组放在我们所谓的链(chain)中。

DNSmasq是一个小巧且方便地用于配置DNSDHCP的工具,适用于小型网络,它提供了DNS功能和可选择的DHCP功能。它服务那些只在本地适用的域名,这些域名是不会在全球的DNS服务器中出现的。DHCP服务器和DNS服务器结合,并且允许DHCP分配的地址能在DNS中正常解析,而这些DHCP分配的地址和相关命令可以配置到每台主机中,也可以配置到一台核心设备中(比如路由器),DNSmasq支持静态和动态两种DHCP配置方式。

 

下面我们就开始编译相关可执行的命令行文件!

 

5.       编译iwconfig命令行文件

   总的来说,编译这个命令行文件很是顺利.

   <1>.下载wireless_tools.29.tar.gz

   <2>. ubantu10.04下解压,交叉编译

       #tar zxvf wireless_tools.29.tar.gz

       #cd  wireless_tools.29

       #gedit Makefile

 

       修改如下地方:

          ## Compiler to use (modify this for cross compile).

          CC = arm-none-linux-gnueabi-gcc

          #CC = gcc

          ## Other tools you need to modify for cross compile (static lib only).

          AR = arm-none-linux-gnueabi-ar

          RANLIB = arm-none-linux-gnueabi-ranlib

          #AR = ar

          #RANLIB = ranlib

      

      然后编译

      #make

      编译完成后,会生成6个可执行文件:

      iwconfig \ iwevent \ iwgetid \ iwlist \ iwpriv \ iwspy

 

      adbiwconfig上传到/system/bin目录下

      #adb push iwconfig /system/bin

      adb shell里执行

      #iwconfig --help

      提示:iwconfig不是一个可执行文件,解决方法就是加上可执行权限(x)

      #chmod 0777 /system/bin/iwconfig

      而后在执行:iwconfig --help

      提示iwconfig not found

 

      后才发现Makefile还有一个选项,选择是否编译成static

      我将BUILD_STATIC = y打开后,重新编译,

      重复上传步骤,发现iwconfig可以正常用了,just so happy!

 

6.       现在就可以开始用iwconfig来命令配置softap了。

具体命令行流程如下:

<1>.load dirver

  insmod /drv/nano_if.ko nrx_fw_path=/drv/x_mac.axf;insmod /drv/nano_ksdio.ko

 

<2>. config softAP

  iwconfig wlan0 mode master

  iwconfig wlan0 channel 1

  iwconfig wlan0 essid HuaziNanoAP

 

<3>.config ip address

  ifconfig wlan0 192.168.43.1;ifconfig wlan0 up

 

<4>.config iptables

       echo 1 > /proc/sys/net/ipv4/ip_forward

       cat /proc/sys/net/ipv4/ip_forward

 

<5>.create share net chain

  iptables -A FORWARD -i eth0 -o wlan0 -m state --state ESTABLISHED,RELATED -j ACCEPT

  iptables -A FORWARD -i wlan0 -o eth0 -j ACCEPT

  iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE

 

<6>.config dnsmasq

dnsmasq --no-daemon --no-resolv --no-poll --dhcp-range=192.168.43.100,192.168.43.200,

100h

 

如此配置后,能后手机搜索到softap : HuaziNanoAP,没有加密的,并且也能正常获得ip地址,但是手机并不能正常的上网。

 

查找原因后知道:dnamasq没有配置dns服务器的地址。

解决方法:

新建一个文件resolv.conf,内容如下:

nameserver 202.96.134.133

nameserver 202.96.128.86

nameserver 8.8.8.8

nameserver 4.2.2.2

 

其中202.96.134.133202.96.128.86是我们办公室网线上网时获得到的dns服务器地址.

8.8.8.84.2.2.2是两个免费的dns服务器.

 

resolv.conf通过adb上传到/etc目录

修改上面的第六步命令如下:

dnsmasq --no-daemon --no-poll --dhcp-range=192.168.43.100,192.168.43.200,100h

这样的话,启动dnsmasq时,会自动加载/etc/resolv.conf配置dns.

 

后用手机再次测试,这次能正常上网了!(可喜可贺)

 

 

7.       根据SoftapController.cpp中需要的private interface,依照iwconfig命令流程,在wifi drivernanoiw.c中封装出相应的接口

   

封装接口的对应关系如下:

getPrivFuncNum(iface, "START");  à

nano_iwpriv_control_on()

 

getPrivFuncNum(iface, "STOP");  à

nano_iwpriv_control_off()

 

getPrivFuncNum(mIface, "AP_BSS_START");  à

nano_iwpriv_softap_start ()

 

fnum = getPrivFuncNum(mIface, "AP_BSS_STOP");  à

nano_iwpriv_softap_stop ()

 

getPrivFuncNum(argv[2], "AP_SET_CFG");  à

nano_iwpriv_set_ap_config()

 

getPrivFuncNum(iface, "FW_RELOAD");  à

nano_iwpriv_fw_reload ()

 

nano_iwpriv_softap_start调用driver的相关api实现如下命令行的流程:

  iwconfig wlan0 mode master

  iwconfig wlan0 channel 1

  iwconfig wlan0 essid HuaziNanoAP

 

 

nano_iwpriv_softap_start依次调用了:

//SET Mode

nrx_iw_set_mode()

//Set Channel

nrx_iw_set_freq()

//SET ESSID

nrx_iw_set_essid()

 

而后,编译后,我们发现在Android设置里,能正常启动不加密softap了,

并且后边的iptables/dnsmasq流程在android code是正常的。

用手机测试能DHCP连接到softap,且能正常上网!

 

至此,softapandroid2.3.4上,不加密时就OK了!

 

8.        在这个“蹭网”现象很普遍的时代,wifi ap不加密是万万不行滴!

     加密势在必行。

 

     下面开始调试softap的加密功能:

 

 其实要实现WEP(有线等效加密)加密还是很容易的,但是WEP加密体制缺陷,通过收集足够的数据包,使用分析加密算法还原出密码,形象地称为 塑料锁”,也即有锁好似无锁,但“有胜于无”。

 

实现wep加密,用iwconfig就能实现。

在第6步的<2>. config softAP增加一句命令即可:

iwconfig wlan0 key s:1234efghijklm

 

后按照第6步启动softap,这时用手机搜到的softap显示wep加密保护,输入密码“1234efghijklm”后,能自动获取到IP,同时也能正常上网

 

需要注意的是:

WEP密码长度必须是5BYTE13BYTE两种,不过一般设13byte,这样破解起来也需时久些!

 

根据命令流程,在、在nano_iwpriv_softap_start调用driver的相关api实现wep,

nano_iwpriv_softap_start调用了:

       if (strcmp(my_ap.sec, "wpa2-psk") == 0)

       {

        ……

              res = nrx_iw_set_encodeext(dev, info, &wrqu->encoding, my_ap.key);

        ……

    }

 

修改android2.3.4\system\netd\ SoftapController.cpp

int SoftapController::setSoftap(int argc, char *argv[]) 函数接口里:

    修改之前:

    if (argc > 6) {

        int j;

        // Use the PKCS#5 PBKDF2 with 4096 iterations

        PKCS5_PBKDF2_HMAC_SHA1(argv[6], strlen(argv[6]),

                reinterpret_cast<const unsigned char *>(ssid), strlen(ssid),

                4096, SHA256_DIGEST_LENGTH, psk);

 

        LOGE("setSoftap psk: \n");

        for (j = 0; j< SHA256_DIGEST_LENGTH; j++)

              LOGE("[%d] = x \n", j, psk[j]);

        

        for (j=0; j < SHA256_DIGEST_LENGTH; j++) {

            sprintf(&psk_str[j<<1], "x", psk[j]);

        }

        psk_str[j<<1] = '\0';

        i = addParam(i, "KEY", psk_str);

    } else {

        i = addParam(i, "KEY", "12345678");

    }

修改之后:

    if (argc > 6) {

        #if 0

        int j;

        // Use the PKCS#5 PBKDF2 with 4096 iterations

        PKCS5_PBKDF2_HMAC_SHA1(argv[6], strlen(argv[6]),

                reinterpret_cast<const unsigned char *>(ssid), strlen(ssid),

                4096, SHA256_DIGEST_LENGTH, psk);

 

        LOGE("setSoftap psk: \n");

        for (j = 0; j< SHA256_DIGEST_LENGTH; j++)

              LOGE("[%d] = x \n", j, psk[j]);

        

        for (j=0; j < SHA256_DIGEST_LENGTH; j++) {

            sprintf(&psk_str[j<<1], "x", psk[j]);

        }

        psk_str[j<<1] = '\0';

        i = addParam(i, "KEY", psk_str);

        #else

        //WEP

        i = addParam(i, "KEY", argv[6]);

        #endif

    } else {

        i = addParam(i, "KEY", "12345678");

    }

 

而后,编译后,我们在Android便携式热点设置里,选择wpa2-psk加密方式,密码设置长度为13byte.启动softap,用手机连接测试softap,显示wep加密保护,正确输入密码连接,能DHCP获得IP,且能正常上网!

 

 

至此,softapandroid2.3.4上,WEP加密时就OK了!

 

9.       接下来,实现wpa加密,需要编译hostapd,这一步是出现问题最多的。

<1>.ubantu10.04arm-none-linux-gnueabi-gcc-4.5.1编译hostapd,开源项目,

nanoradio提供的版本是hostapd_WD_8.3,做了一定修改。

编译命令如下:

make -j4 SPACE=kernel DRIVER_PATH=../driver/src

编译之前,需将nano_7.0.8里的内容拷贝到hostapd_WD_8.3/driver/src目录下。

然后,执行编译命令,

check ../driver/src/userspace/libnrx/编译没有,没有编译,则会去编译

libnrx,但是这个路径下没有Makefile,报错!

 

解决方法:

到路径下查看,发现存在configure.ac make.am,有了这两个文件,我们就可以生成

Makefile.

autoconf根据configure.ac(在早前版本称为configure.in)生成configure

automake,根据Makefile.am,生成Makefile.in

configure,根据Makefile.in生成Makefile

 

所以需要在ubantu10.04安装autoconfautomake两个工具,安装完成后,就可以生成

Makefile了。

 

修改MakefileCC等为ARM交叉编译,以及修改一些地方编译通过后,

会生产一个libnrx.a。这是编译hostapd需要的!

 

之后,修改hostapd_WD_8.3/hostapd/Makefile,同样主要是配置成ARM交叉编译,

在执行编译命令

make -j4 SPACE=kernel DRIVER_PATH=../driver/src

 

这次编译并未保错了,并且生成两个可执行命令行文件hostapdhostapd_cli,

hostapdadb push/system/bin,添加可执行权限后,在adb shell里执行:

#hostapd -v

/system/bin/sh:hostapd:No such file or directory

 

说明hostapd命令行不能用。怎么办?

 

我想:当初编译iwconfig时,打开BUILD_STATIC就可以了,是不是编译hostapd是也要加上呢?

 

先不管,加上试试,在hostapdMakefile

CFLAGS += -static

重新编译,再次上传生成的hostapd/system/bin,添加可执行权限后,执行:

#hostapd -v

/system/bin/sh:hostapd:No such file or directory

 

问题依旧,怎么办?

只好求助百度。

 

网上有人说,降低ARM交叉编译器版本为android编译器的版本。

查了一下,android2.3.4\build\envsetup.sh有如下:

export ANDROID_EABI_TOOLCHAIN=$prebuiltdir/toolchain/arm-eabi-4.4.3/bin

说明用的是交叉编译版本是4.4.3

 

好,开始编译4.4.3arm交叉编译器,这一步还好,很顺利。

 

交叉编译器编译好后,重新配置hostapdMakefile,CCARRANLIB配置成

新编译的版本为4.4.3arm交叉编译。

 

再次编译,上传生成的hostapd/system/bin,添加可执行权限后,执行:

#hostapd -v

/system/bin/sh:hostapd:No such file or directory

 

哎,问题依旧,怎么办?

正当灰心丧气时,总监提出也许可以在android源码里编译。

之前之所以没有这么做,因为Nanoradio提供的方法就是在Ubantu上交叉编译,

问了那边有没有在android编译过,说从来没有过,很少汗颜啊!

没办法,第一个吃螃蟹的人总的有嘛!

好,试试再说!

 

先将hostapd_WD_8.3拷贝到external,

#cd external/hostapd_WD_8.3/hostapd

#mm

直接报错,分析了一下是hostapd src路径没有设置对,

修改android.mksrc ../src

另,修改src/driversdrivers.mksrc 也为 ../src

 

再次mm. 前面编译还挺顺利,但link时出错,需要libnrx.a,

当然这次的libnrx.a也是要用android的编译器编译才行,

driver/src/userspace/libnrx/没有android.mk,怎办?

 

通过Makefile的规则,我增加这个android.mk,

后编译libnrx通过后,再次到hostapd里去编译,

这次通过了。(大喜!)

 

上传生成的hostapd/system/bin,添加可执行权限后,执行:

#hostapd -v

/system/bin/sh:hostapd:No such file or directory

hostapd v0.8.x

User space daemon for IEEE 802.11 AP management,

IEEE 802.1X/WPA/WPA2/EAP/RADIUS Authenticator

Copyright (c) 2002-2011, Jouni Malinen <j@w1.fi> and contributors

 

Yeah, 成功了,hostapd可以用了!编译成功!

 

 

<2>.命令行配置wpa加密的softap

具体命令行流程如下:

1.load dirver

  insmod /drv/nano_if.ko nrx_fw_path=/drv/x_mac.axf;insmod /drv/nano_ksdio.ko

 

2. config softAP

  hostapd /system/etc/hostapd_softap_RSN_TKIP.conf

 

3.config ip address

  ifconfig wlan0 192.168.43.1;ifconfig wlan0 up

 

4.config iptables

       echo 1 > /proc/sys/net/ipv4/ip_forward

       cat /proc/sys/net/ipv4/ip_forward

 

5.create share net chain

  iptables -A FORWARD -i eth0 -o wlan0 -m state --state ESTABLISHED,RELATED -j ACCEPT

  iptables -A FORWARD -i wlan0 -o eth0 -j ACCEPT

  iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE

 

6.config dnsmasq

dnsmasq --no-daemon --no-resolv --no-poll --dhcp-range=192.168.43.100,192.168.43.200,

100h

 

首先修改hostapd_softap_RSN_TKIP.conf中相关配置项:

# AP netdevice name

interface=wlan0

# Driver interface type (hostap/wired/madwifi/prism54/test/none/nl80211/bsd);

driver=nano

ssid=HuaziNanoAP

 

#屏蔽掉以下两个

#ctrl_interface=/var/fun/hostapd

#ctrl_interface_group=0

 

如果不屏蔽掉的话,hostapd命令执行会出错!

出错提示如下:

mkir[ctrl_interface]:No such file or directory

chown[ctrl_interface]:Operation not permitted

 

 

上传hostapd_softap_RSN_TKIP.conf/system/etc,

执行上述的命令流程,wpa加密的softap就配置出来了。

手机测试,连接OK!

 

 

<3>.根据nanoradio提供的android2.3.4 sdk,整合相关内容。

config.xml:

softap interface改成sap0 ,防止与wifi client冲突,如果两个接口同为wlan0的话,启动client时,也会触发启动softap,流程会出错的!

 

init.rc:增加wifi clientsoftap相关的service

 

wifi.c: 修改。

 

SoftapController.cpp: 修改。

 

命令行脚本: 修改。

 

之后在此基础上调试,clientsoftapOK了!

 

本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
android wifi热点代码流程跟踪分析
Wifi模块
嵌入式Linux系列第9篇:使用WIFI
旅行时通过树莓派和 iPad Pro 备份图片
ESP8266 入门-NONSDK-LED-UDP
ESP8266 wifi模块开发汇总
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服