如何在LTE模式和STA(WIFI)模式下,做到极速切换,保证互联网是通的。
说明:
有一个MIFI路由器,可以通过LTE模式上网,也就是插4G网卡上网(就叫LTE模式)。
也可以通过WIFI连接到其他的WIFI上网,类似于信号放大器,磁力猫这类的(就叫WIFI模式)。
有一个Auto模式,就是尽量保证用户上网是ok的。保证用户上网为第一优先级。如果WIFI模式可以上网,通过WiFi上网,如果发现wifi不通切到lte,如果在lte模式,发现wifi又可以上网,就自动切到wifi。
1.这个wifi以前是连接过的,有链接的信息(即ssid,密码啥的)
2.当前这个wifi存在,能扫描到这个wifi
3.如果需要极速切到wifi的话,还得确保这个wifi是可以上网的。但是如果不切过去,那就不知道能不能上网,如果切过去不能上网,又和需求不一致。
就需要在LTE上网的时候,后台先扫描wifi,然后存在的话,连接wifi。通过wifi连接的网口进行ping这类的动作,如果发现可以上网。就直接切过去。用户会感觉1秒左右的断网,影响到最小。
1 检测WIFI的wan口是否存在,如果down掉的话,up起来
check wlan0 is or not up. if not, up the wlan0(5g)
2 添加一个标识(WIFI标识),为后面的步骤4使用
add flag for uplink
3上连到要连接的WIFI
uplink the 5G ssid
4 udhcp分配ip
udhcpc
5 删除标识
del the flag
6 检测这个WIFI是否可以连通
check whether 5G AP is connected to the Internet
步骤4,连接到MIFI路由器的设备,client是要被dhcp分配ip的。在执行第4步骤的时候
udhcpc -i wlan0会重新执行 package/network/config/netifd/files/usr/share/udhcpc/default.script
这个脚本,重新删除以前的ip,分配新的ip。
那么我们在步骤4的时候,default.script里面检测到 WIFI标识(步骤2) 的话,就给wifi分配一个路由。这样步骤6才可以去检测WIFI是否连接。也就是wifi模式走wifi模式的路由,lte模式走lte的路由,互不影响。
没检测 WIFI标识 到的话就按以前的方式删除旧的路由。我感觉,已经连接的client的路由是不会删除掉的吧。
步骤6的ping -c 2 -I wlan0 -W 2 8.8.8.8
//通过wlan0口上网,wlan0设置的是wifi模式的接口
int check_connect_internet_staus_by_5g_ap()
{
int online;
int flag1 = 0;
int flag2 = 0;
//ping -c 5 -I wlan0 www.baidu.com
online = system("ping -c 2 -I wlan0 -W 2 8.8.8.8");
//my_printf(LOG_MODE_LEVEL_5,"%s(%d) online:%d\n",__FUNCTION__,__LINE__, online);
if(online == 0)
flag1 = 1; //online
else
flag1 = 0; //offline
sleep(2);
online = system("ping -c 2 -I wlan0 -W 2 www.baidu.com");
//my_printf(LOG_MODE_LEVEL_5,"%s(%d) online:%d\n",__FUNCTION__,__LINE__, online);
if(online == 0)
flag2 = 1; //online
else
flag2 = 0; //offline
sleep(2);
//my_printf(LOG_MODE_LEVEL_3,"%s(%d) flag1:%d flag2:%d\n",__FUNCTION__,__LINE__, flag1,flag2);
if( (flag1 == 1) || (flag2 == 1) )
return 1;
else
return 0;
}
//if the 5g Ap can connect the internet. return 1 ,otherwise return 0
int get_uplink_5G_internect_status()
{
char cmd[BUF_SIZE_128] = {0};
char tmp_buf[BUF_SIZE_128] = {0};
char securitu_mode[256] = {0};
char value[256] = {0};
int uplink_5g_connect_status=0; // 1 connect_internet, 0 not_connect, default is 0
//1.check wlan0 is or not up. if not, up the wlan0(5g)
sprintf(cmd, "ifconfig | grep -r wlan0");
cusapp_base_printf(CUSAPP_BASE_LOG_LEVEL_1, "%s(%d) .......cmd:%s\n",__FUNCTION__,__LINE__,cmd);
get_system_output(cmd, tmp_buf, sizeof(tmp_buf));
cusapp_base_printf(CUSAPP_BASE_LOG_LEVEL_1, "%s(%d) tmp_buf=%s\n",__FUNCTION__,__LINE__, tmp_buf);
if( openUtil_strlen(tmp_buf) == 0 )//wlan0 is not up
{
system("ifconfig wlan0 up");
}
//2. add flag for uplink
system("touch /tmp/uplink_5g_prepare_flag");
//3.uplink the 5G ssid
system("killall wpa_supplicant");
memset(value, 0x0, sizeof(value));
GetNVRamData("/etc/config/uplink.uplink_info.securitu_mode", value, sizeof(value));
openUtil_strcpy(securitu_mode, value);
if( openUtil_strcasecmp(securitu_mode, "share") == 0 ) //No psw,share
{
system("wpa_supplicant -Dnl80211 -iwlan0 -c /etc/uplink/wpa_share.conf &");
}
else //wpa_encry
{
system(" wpa_supplicant -Dnl80211 -iwlan0 -c /etc/uplink/wpa_encry.conf &");
}
sleep(2);
//4.udhcpc
system("udhcpc -i wlan0");
sleep(2);
//5. del the flag
system("rm /tmp/uplink_5g_prepare_flag");
//6.check whether 5G AP is connected to the Internet
uplink_5g_connect_status = check_connect_internet_staus_by_5g_ap();
if(uplink_5g_connect_status == 0) //not_connect_internet
{
return 0;
}
else
{
return 1;
}
}
如果这个WIFI是可以上网的,就可以切到WIFI模式
if(uplink_5g_ap_status == 1) //5g ap connect the internet
{
cusapp_base_printf(CUSAPP_BASE_LOG_LEVEL_1, "%s(%d) 5g ap internet status uplink_5g_ap_status:%d...........\n",__FUNCTION__,__LINE__,uplink_5g_ap_status);
ret_config = switch_to_wifi_mode();
cusapp_base_printf(CUSAPP_BASE_LOG_LEVEL_1, "%s(%d) switch_to_wifi_mode=ret_config:%d 1_ok 0_error\n",__FUNCTION__,__LINE__,ret_config);
/*
if( openUtil_strcasecmp(securitu_mode, "share") == 0 ) //No psw,share
{
system("sh /etc/uplink/uplink.sh share");
}
else//wpa_encry
{
system("sh /etc/uplink/uplink.sh encry");
}
*/
}
else
{
cusapp_base_printf(CUSAPP_BASE_LOG_LEVEL_1, "%s(%d) 5g ap cann't connect the internet,do noting.............\n",__FUNCTION__,__LINE__);
}
步骤4执行的脚本
差别在uplink_5g_flag那片
#!/bin/sh
[ -z "$1" ] && echo "Error: should be run by udhcpc" && exit 1
uplink_5g_flag="/tmp/uplink_5g_prepare_flag"
set_classless_routes() {
local max=128
local type
while [ -n "$1" -a -n "$2" -a $max -gt 0 ]; do
[ ${1##*/} -eq 32 ] && type=host || type=net
echo "udhcpc: adding route for $type $1 via $2"
route add -$type "$1" gw "$2" dev "$interface"
max=$(($max-1))
shift 2
done
}
setup_interface() {
echo "udhcpc: ifconfig $interface $ip netmask ${subnet:-255.255.255.0} broadcast ${broadcast:-+}"
ifconfig $interface $ip netmask ${subnet:-255.255.255.0} broadcast ${broadcast:-+}
[ -n "$router" ] && [ "$router" != "0.0.0.0" ] && [ "$router" != "255.255.255.255" ] && {
echo "udhcpc: setting default routers: $router"
local valid_gw=""
for i in $router ; do
echo "################ $i $interface"
if [ -f "$uplink_5g_flag" ];
then
echo "###############uplink_5g_flag"
route add default gw $i dev $interface metric 10
else
echo "###############no uplink_5g_flag"
route add default gw $i dev $interface
fi
valid_gw="${valid_gw:+$valid_gw|}$i"
done
echo "###############del---gw#####"
if [ -f "$uplink_5g_flag" ];
then
echo "###############delgw donoting"
else
echo "###############del gw $1 gw $2"
eval $(route -n | awk '
/^0.0.0.0\W{9}('$valid_gw')\W/ {next}
/^0.0.0.0/ {print "route del -net "$1" gw "$2";"}
')
fi
# eval $(route -n | awk '
# /^0.0.0.0\W{9}('$valid_gw')\W/ {next}
# /^0.0.0.0/ {print "route del -net "$1" gw "$2";"}
# ')
}
# CIDR STATIC ROUTES (rfc3442)
[ -n "$staticroutes" ] && set_classless_routes $staticroutes
[ -n "$msstaticroutes" ] && set_classless_routes $msstaticroutes
}
applied=
case "$1" in
deconfig)
ifconfig "$interface" 0.0.0.0
;;
renew)
setup_interface update
;;
bound)
setup_interface ifup
;;
esac
# user rules
[ -f /etc/udhcpc.user ] && . /etc/udhcpc.user
exit 0