360 (2代)无线WIFI(网卡)驱动移植和相关的无线工具编译安装
一、前言
本篇文章要的做的事情是,移植一款USB WIFI芯片的驱动到嵌入式Linux环境下,让嵌入式开发板能够通过这款USB WIFI实现上网,说白了就是安装无线网卡驱动。
这款USB-WIFI无线网卡型号是:MT7601,这是Ralink(雷凌科技) 出品的芯片,是一款USB协议的WIFI。目前这款芯片被很多厂家制作成随身WIFI使用了,比如:百度的小度WIFI,小米的WIFI,360的随身WIFI一代等等,都是采用这款芯片。在电脑上使用当然很简单,直接下载官方驱动一安装就可以使用。如果要在嵌入式Linux环境下使用,就没有现成的驱动可以安装,需要自己写,自己写不出来怎么办? 那就看官方有没有源码,刚好MT7601这款芯片在官网上提供了Linux下源码下载链接。然后就有了这篇文章。 将源码下载下来要根据自己的开发环境进行配置源码然后编译,生成驱动ko文件之后,安装就行了。 光安装驱动还不行,还需要安装移植WIFI的管理工具,然后才方便操作WIFI做一些事情:比如:扫描周边热点,列出信号强度和名称,连接指定WIFI,指定连接协议等等。
二、移植流程
步骤1: 下载官方的驱动源码,移植修改编译工具,arm-linux-gcc。 -------生成一个文件xxx.ko:
步骤2: 编译、安装相关的无线WIFI管理工具: 无线加密协议、WIFI启动工具、WIFI扫描工具……
在解压的源码目录下编译源码,生成驱动文件。 (需要在解压的顶层目录下输入 make) 编译成功后,会在 os/linux/目录下生成 mt7601Usta.ko 文件。
步骤3: 配置动态IP分配功能。
步骤4: 配置UBOOT环境变量,设置开发板本地挂载启动。
UBOOT环境变量设置:
三、安装WIFI管理工具,启动WIFI连接进行测试
WIFI环境配置、连接热点上网的流程总结:
1. 将WIFI相关的工具库所需要的库文件和可执行文件拷贝到对应的目录(开发板根目录)下。 2. mkdir /var/run/wap_supplicant -p #创建网卡控制接口 3. 为了支持自动IP地址分配,拷贝所需要的文件到指定的目录下。 #创建自动获取IP地址的文件 mkdir /usr/share/udhcpc -p cp simple.script /usr/share/udhcpc/default.script -fv 4. 安装驱动: insmod mt7601Usta.ko 5. 启动网卡,并连接指定的热点: wpa_supplicant -Dwext -ira0 -c /etc/wpa_supplicant.conf -B 6. 自动分配IP地址: udhcpc -i ra0 |
详细步骤如下:
(1) 安装WIFI驱动,同时将360WIFI插到开发板的USB口上
(2)查看所有的网卡
(3)启动网卡
(4) 扫描周边WIFI(热点)
(5)通过命令,启动网卡,并连接指定的热点
(6)查看WIFI当前连接的信息
(7)向路由器请求动态分配一个IP地址
(8)测试WIFI连接外网
四、socket编程测试代码(TCP服务器代码)
为了直观的测试WIFI是否能够正常联网通信,这里编写一份TCP服务器代码,在局域网的电脑上打开网络调试助手进行连接进行数据收发。
#include <stdio.h>
#include <sys/types.h> /* See NOTES */
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netinet/in.h>
/*
函数功能: 创建TCP服务器
*/
int CreateTCP_Server(int server_port)
{
/*1. 创建TCP服务器套接字*/
int server_fd=socket(AF_INET,SOCK_STREAM,0);
if(server_fd<0)
{
return -1;
}
/*2. 绑定端口号: 创建服务器*/
struct sockaddr_in server_addr;
server_addr.sin_family=AF_INET; //IPV4
server_addr.sin_port=htons(server_port); //将小端字节序转为大端字节序
server_addr.sin_addr.s_addr=INADDR_ANY; //表示本地的所有IP地址(0.0.0.0)
if(bind(server_fd,(const struct sockaddr*)&server_addr, sizeof(struct sockaddr)))
{
return -2;
}
/*3. 设置服务器监听的客户端数量*/
if(listen(server_fd,20)!=0)
{
return -3;
}
/*4. 等待客户端连接*/
struct sockaddr_in client_addr;
socklen_t addrlen=sizeof(struct sockaddr);
int client_fd=accept(server_fd,(struct sockaddr*)&client_addr,&addrlen);
if(client_fd<0)
{
return -4;
}
printf("连接的客户端IP地址:%s\n",inet_ntoa(client_addr.sin_addr)); //整型IP地址转字符串IP地址
printf("连接的客户端端口号:%d\n",ntohs(client_addr.sin_port)); //大端转小端
return client_fd;
}
/*
功能: 创建TCP服务器
*/
int main(int argc,char **argv)
{
if(argc!=2)
{
printf("参数格式: ./server_app <端口号>\n");
//0~65535 ,大于1024
return 0;
}
/*1. 创建TCP服务器*/
int client_fd;
client_fd=CreateTCP_Server(atoi(argv[1]));
if(client_fd<0)
{
printf("服务器创建失败! 错误值:%d\n",client_fd);
return 0;
}
/*2. 进行网络数据通信*/
int len=write(client_fd,"123456789",10);
printf("服务器成功发送:%d字节.\n",len);
return 0;
}