精华内容
下载资源
问答
  • 本文分享了iptable防火墙状态异常导致丢包的排查记录,这个排查过程非常曲折,最后使用了在现在的作者看来非常落伍的工具:systemtap,才得以排查成功。其实依作者现有的经验,此问题现在仅需一条命令即可找到原因,...

    0.导语

    K8s容器网络涉及诸多内核子系统,IPVS,Iptable,3层路由,2层转发,TCP/IP协议栈,这些复杂的内核子系统在特定场景下可能会遇到设计者最初也想不到的问题。

    本文分享了iptable防火墙状态异常导致丢包的排查记录,这个排查过程非常曲折,最后使用了在现在的作者看来非常落伍的工具:systemtap,才得以排查成功。其实依作者现有的经验,此问题现在仅需一条命令即可找到原因,这条命令就是作者之前分享过文章使用 ebpf 深入分析容器网络 dup 包问题中提到的skbtracker。时隔7个月,这个工具已经非常强大,能解决日常网络中的90%的网络问题。

    此文其实已于2019年7月在腾讯内部进行发表,时隔一年,再次翻出来阅读仍然有颇多收获,因此把它分享出来给其他同行一起学习。此外,本篇文章也将作为开篇,后续陆续分享作者近期使用ebpf工具排查各种内核疑难杂症的过程及经验。

    1. 问题描述

    腾讯内部某业务在容器场景上遇到了一个比较诡异的网络问题,在容器内使用GIT,SVN工具从内部代码仓库拉取代码偶发性卡顿失败,而在容器所在的Node节点使用同样版本的GIT,SVN工具却没有问题。用诡异这个词,是因为这个问题的分析持续时间比较久,经历了多个同学之手,最后都没有揪出问题根源。有挑战的问题排查对于本人来说是相当有吸引力的,于是在手头没有比较紧急任务的情况下,便开始了有趣的debug。

    从客户描述看,问题复现概率极大,在Pod里面拉取10次GIT仓库,必然有一次出现卡死,对于必现的问题一般都不是问题,找到复现方法就找到了解决方法。从客户及其他同事反馈,卡死的时候,GIT Server不再继续往Client端发送数据,并且没有任何重传。

    1.1 网络拓扑

    业务方采用的是TKE单网卡多IP容器网络方案,node自身使用主网卡eth0,绑定一个ip,另一个弹性网卡eth1绑定多个ip地址,通过路由把这些地址与容器绑定,如图1-1.

    a284e7d72e3d6e58d0b9c7cd8ea310f2.png

    图 1-1 TKE单网卡多IP容器网络

    1.2 复现方法

    undefined_b.jpg

    1.3 抓包文件分析

    在如下三个网口eth1,veth_a1,veth_b1分别循环抓包,Server端持续向Client发送大包,卡顿发生时,Server端停止往Client发送数据包,没有任何重传报文。

    2. 排查过程

    分析环境差异:node和Pod环境差异

    • Node内存比Pod多,而Node和Pod的TCP 接收缓存大小配置一致,此处差异可能导致内存分配失败。
    • 数据包进出Pod比Node多了一次路由判断,多经过两个网络设备:veth_a1和veth_b1,可能是veth的某种设备特性与TCP协议产生了冲突,或veth虚拟设备有bug,或veth设备上配置了限速规则导致。

    分析抓包文件: 有如下特征

    • 两个方向的数据包,在eth1,veth_a1设备上都有被buffer的现象:到达设备一段时间后被集中发送到下一跳
    • 在卡住的情况下,Server端和Client端都没有重传,eth1处抓到的包总比veth_a1多很多,veth_a1处抓到的包与veth_b1处抓到的包总是能保持一致

    分析:TCP是可靠传输协议,如果中间因为未知原因(比如限速)发生丢包,一定会重传。因此卡死一定是发包端收到了某种控制信号,主动停止了发包行为。

    猜测一:wscal协商不一致,Server端收到的wscal比较小

    在TCP握手协商阶段,Server端收到Client端wscal值比实际值小。传输过程中,因为Client端接收buffer还有充裕,Client端累计一段时间没及时回复ack报文,但实际上Server端认为Client端窗口满了(Server端通过比较小的wscal推断Client端接收buffer满了),Server端会直接停止报文发送。

    如果Server端使用IPVS做接入层的时候,开启synproxy的情况下,确实会导致wscal协商不一致。

    带着这个猜想进行了如下验证:

    • 通过修改TCP 接收buffer(ipv4.tcp_rmem)大小,控制Client wscal值
    • 通过修改Pod内存配置,保证Node和Pod的在内存配置上没有差异
    • 在Server端的IPVS节点抓包,确认wscal协商结果

    以上猜想经过验证一一被否决。并且找到业务方同学确认,虽然使用了IPVS模块,但是并没有开启synproxy功能,wscal协商不一致的猜想不成立。

    猜测二:设备buffer了报文

    设备开启了TSO,GSO特性,能极大提升数据包处理效率。猜测因为容器场景下,经过了两层设备,在每层设备都开启此特性,每层设备都buffer一段,再集中发送,导致数据包乱序或不能及时送到,TCP层流控算法判断错误导致报文停止发送。

    带着这个猜想进行了如下验证:

    1)关闭所有设备的高级功能(TSO,GSO,GRO,tx-nocache-copy,SG)

    2)关闭容器内部delay ack功能(net.ipv4.tcp_no_delay_ack),让Client端积极回应Server端的数据包

    以上猜想也都验证失败。

    终极方法:使用systamp脚本揪出罪魁祸首

    验证了常规思路都行不通。但唯一肯定的是,问题一定出在CVM内部。注意到eth1抓到的包总是比veth_a1多那么几个,之前猜想是被buffer了,但是buffer了总得发出来吧,可是持续保持抓包状态,并没有抓到这部分多余的包,那这部分包一定被丢了。这就非常好办了,只要监控这部分包的丢包点,问题就清楚了。使用systemtap监控skb的释放点并打印backtrace,即可快速找到引起丢包的内核函数。Systemtap脚本如图2-1,2-2所示。

    a778d1c3d05e295f6ecc2963a018a5bc.png

    图2-1 dropwatch脚本(不带backtrce打印)

    ea5fce0b708cdd589606227ca41e4c64.png


    图2-2 dropwatch脚本(带backtrce打印)

    首先通过图2-1脚本找到丢包点的具体函数,然后找到丢包具体的地址(交叉运行stap --all-modules dropwatch.stp -g和stap dropwatch.stp -g命令,结合/proc/kallsyms里面函数的具体地址),再把丢包地址作为判断条件,精确打印丢包点的backtrace(图2-2)。

    运行脚本stap --all-modules dropwatch.stp -g,开始复现问题,脚本打印如图2-3:

    2cb62681ef67f429de3e1374eb2cea16.png


    图2-3 丢包函数

    正常不卡顿的时候是没有nf_hook_slow的,当出现卡顿的时候,nf_hook_slow出现在屏幕中,基本确定丢包点在这个函数里面。但是有很多路径能到达这个函数,需要打印backtrace确定调用关系。再次运行脚本:stap dropwatch.stp -g,确认丢包地址列表,对比/proc/kallsyms符号表ffffffff8155c8b0 T nf_hook_slow,找到最接近0xffffffff8155c8b0 的那个值0xffffffff8155c9a3就是我们要的丢包点地址(具体内核版本和运行环境有差异)。加上丢包点的backtrace,再次复现问题,屏幕出现图2-4打印。

    aef6808cda66d6f41d9fea28ba59fc4a.png

    图2-4 丢包点backtrace

    undefined_b.jpg


    图2-5连接表状态

    可以看出ip_forward调用nf_hook_slow最终丢包。很明显数据包被iptable上的FORWARD 链规则丢了。查看FORWARD链上的规则,确实有丢包逻辑(-j REJECT --reject-with icmp-port-unreachable),并且丢包的时候一定会发 icmp-port-unreachable类型的控制报文。到此基本确定原因了。因为是在Node上产生的icmp回馈信息,所以在抓包的时候无法通过Client和Server的地址过滤出这种报文(源地址是Node eth0地址,目的地址是Server的地址)。同时运行systamp脚本和tcpdump工具抓取icmp-port-unreachable报文,卡顿的时候两者都有体现。

    接下来分析为什么好端端的连接传输了一段数据,后续的数据被规则丢了。仔细查看iptalbe规则发现客户配置的防火墙规则是依赖状态的:-m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT。只有ESTABLISHED连接状态的数据包才会被放行,如果在数据传输过程中,连接状态发生变化,后续入方向的报文都会被丢弃,并返回端口不可达。通过conntrack工具监测连接表状态,发现出问题时,对应连接的状态先变成了FIN_WAIT,最后变成了CLOSE_WAIT(图2-5)。通过抓包确认,GIT在下载数据的时候,会开启两个TCP连接,有一个连接在过一段时间后,Server端会主动发起fin包,而Client端因为还有数据等待传输,不会立即发送fin包,此后连接状态就会很快发生如下切换:

    ESTABLISHED(Server fin)->FIN_WAIT(Client ack)->CLOSE_WAIT

    所以后续的包就过不了防火墙规则了(猜测GIT协议有一个控制通道,一个数据通道,数据通道依赖控制通道,控制通道状态切换与防火墙规则冲突导致控制通道异常,数据通道也跟着异常。等有时间再研究下GIT数据传输相关协议)。这说明iptables的有状态的防火墙规则没有处理好这种半关闭状态的连接,只要一方(此场景的Server端)主动CLOSE连接以后,后续的连接状态都过不了规则(-m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT)。

    明白其中原理以后,对应的解决方案也比较容易想到。因为客户是多租户容器场景,只放开了Pod主动访问的部分服务地址,这些服务地址不能主动连接Pod。了解到GIT以及SVN都是内部服务,安全性可控,让用户把这些服务地址的入方向放行,这样即使状态发生切换,因为满足入向放行规则,也能过防火墙规则。

    3. 思考

    在排查问题的过程中,发现其实容器的网络环境还有非常多值得优化和改进的地方的,比如:

    • TCP接受发送buffer的大小一般是在内核启动的时候根据实际物理内存计算的一个合理值,但是到了容器场景,直接继承了Node上的默认值,明显是非常不合理的。其他系统资源配额也有类似问题。
    • 网卡的TSO,GSO特性原本设计是为了优化终端协议栈处理性能的,但是在容器网络场景,Node的身份到底是属于网关还是终端?属于网关的话那做这个优化有没有其他副作用(数据包被多个设备buffer然后集中发出)。从Pod的角度看,Node在一定意义上属于网关的身份,如何扮演好终端和网关双重角色是一个比较有意思的问题
    • Iptables相关问题

    此场景中的防火墙状态问题

    规则多了以后iptables规则同步慢问题

    Service 负载均衡相关问题(规则加载慢,调度算法单一,无健康检查,无会话保持,CPS低问题)

    SNAT源端口冲突问题,SNAT源端口耗尽问题

    • IPVS相关问题

    统计timer在配置量过大时导致CPU软中断收包延时问题

    net.ipv4.vs.conn_reuse_mode导致的一系列问题 (参考:https://github.com/kubernetes/kubernetes/issues/81775

    截止到现在,以上大多数问题已经在TKE平台得到解决,部分修复patch提到了内核社区,相应的解决方案也共享到了K8s社区。

    【腾讯云原生】云说新品、云研新术、云游新活、云赏资讯,关注同名公众号,及时获取更多干货!!
    展开全文
  • VB写的,如果不能运行,安装vb6 网络状态 测试工具 PING 掉包 记录 测试 超时时间可设置
  • 文章来源:腾讯云原生 /原文链接文章作者杨玉玺,2011年至今一直从事底层网络研发,目前就职腾讯云 TKE 团队,专注 K8s 底层网络。先后就职于阿里云、金山云从事 VPC 虚拟化网络研发,对高性能网络优化,复杂网络...

    4b4bf3003f619dc26f4a4cabcd44d4d7.gif

    文章来源:腾讯云原生 / 原文链接文章作者杨玉玺,2011年至今一直从事底层网络研发,目前就职腾讯云 TKE 团队,专注 K8s 底层网络。先后就职于阿里云、金山云从事 VPC 虚拟化网络研发,对高性能网络优化,复杂网络问题排查有非常丰富的经验。导语

    K8s容器网络涉及诸多内核子系统,IPVS,Iptable,3层路由,2层转发,TCP/IP协议栈,这些复杂的内核子系统在特定场景下可能会遇到设计者最初也想不到的问题。本文分享了iptable防火墙状态异常导致丢包的排查记录,这个排查过程非常曲折,最后使用了在现在的作者看来非常落伍的工具:systemtap,才得以排查成功。其实依作者现有的经验,此问题现在仅需一条命令即可找到原因,这条命令就是作者之前分享过文章使用 ebpf 深入分析容器网络 dup 包问题中提到的skbtracker。时隔7个月,这个工具已经非常强大,能解决日常网络中的90%的网络问题。此文其实已于2019年7月在腾讯内部进行发表,时隔一年,再次翻出来阅读仍然有颇多收获,因此把它分享出来给其他同行一起学习。此外,本篇文章也将作为开篇,后续陆续分享作者近期使用ebpf工具排查各种内核疑难杂症的过程及经验。1. 问题描述腾讯内部某业务在容器场景上遇到了一个比较诡异的网络问题,在容器内使用GIT,SVN工具从内部代码仓库拉取代码偶发性卡顿失败,而在容器所在的Node节点使用同样版本的GIT,SVN工具却没有问题。用诡异这个词,是因为这个问题的分析持续时间比较久,经历了多个同学之手,最后都没有揪出问题根源。有挑战的问题排查对于本人来说是相当有吸引力的,于是在手头没有比较紧急任务的情况下,便开始了有趣的debug。从客户描述看,问题复现概率极大,在Pod里面拉取10次GIT仓库,必然有一次出现卡死,对于必现的问题一般都不是问题,找到复现方法就找到了解决方法。从客户及其他同事反馈,卡死的时候,GIT Server不再继续往Client端发送数据,并且没有任何重传。

    1.1 网络拓扑

    业务方采用的是TKE单网卡多IP容器网络方案,node自身使用主网卡eth0,绑定一个ip,另一个弹性网卡eth1绑定多个ip地址,通过路由把这些地址与容器绑定,如图1-1.
    1056254dcf0ee0f74d530133104dce4f.png

    1.2 复现方法

    7ed3845e8cdb82f07070a6183bbf83cc.png

    1.3 抓包文件分析

    在如下三个网口eth1,veth_a1,veth_b1分别循环抓包,Server端持续向Client发送大包,卡顿发生时,Server端停止往Client发送数据包,没有任何重传报文。2. 排查过程

    分析环境差异:Node和Pod环境差异

    • Node内存比Pod多,而Node和Pod的TCP 接收缓存大小配置一致,此处差异可能导致内存分配失败。
    • 数据包进出Pod比Node多了一次路由判断,多经过两个网络设备:veth_a1和veth_b1,可能是veth的某种设备特性与TCP协议产生了冲突,或veth虚拟设备有bug,或veth设备上配置了限速规则导致。

    分析抓包文件: 有如下特征

    • 两个方向的数据包,在eth1,veth_a1设备上都有被buffer的现象:到达设备一段时间后被集中发送到下一跳
    • 在卡住的情况下,Server端和Client端都没有重传,eth1处抓到的包总比veth_a1多很多,veth_a1处抓到的包与veth_b1处抓到的包总是能保持一致
    分析:TCP是可靠传输协议,如果中间因为未知原因(比如限速)发生丢包,一定会重传。因此卡死一定是发包端收到了某种控制信号,主动停止了发包行为。

    猜测一:wscal协商不一致,Server端收到的wscal比较小

    在TCP握手协商阶段,Server端收到Client端wscal值比实际值小。传输过程中,因为Client端接收buffer还有充裕,Client端累计一段时间没及时回复ack报文,但实际上Server端认为Client端窗口满了(Server端通过比较小的wscal推断Client端接收buffer满了),Server端会直接停止报文发送。如果Server端使用IPVS做接入层的时候,开启synproxy的情况下,确实会导致wscal协商不一致。带着这个猜想进行了如下验证:
    • 通过修改TCP 接收buffer(ipv4.tcp_rmem)大小,控制Client wscal值
    • 通过修改Pod内存配置,保证Node和Pod的在内存配置上没有差异
    • 在Server端的IPVS节点抓包,确认wscal协商结果
    以上猜想经过验证一一被否决。并且找到业务方同学确认,虽然使用了IPVS模块,但是并没有开启synproxy功能,wscal协商不一致的猜想不成立。

    猜测二:设备buffer了报文

    设备开启了TSO,GSO特性,能极大提升数据包处理效率。猜测因为容器场景下,经过了两层设备,在每层设备都开启此特性,每层设备都buffer一段,再集中发送,导致数据包乱序或不能及时送到,TCP层流控算法判断错误导致报文停止发送。带着这个猜想进行了如下验证:1)关闭所有设备的高级功能(TSO,GSO,GRO,tx-nocache-copy,SG)2)关闭容器内部delay ack功能(net.ipv4.tcp_no_delay_ack),让Client端积极回应Server端的数据包以上猜想也都验证失败。

    终极方法:使用systamp脚本揪出罪魁祸首

    验证了常规思路都行不通。但唯一肯定的是,问题一定出在CVM内部。注意到eth1抓到的包总是比veth_a1多那么几个,之前猜想是被buffer了,但是buffer了总得发出来吧,可是持续保持抓包状态,并没有抓到这部分多余的包,那这部分包一定被丢了。这就非常好办了,只要监控这部分包的丢包点,问题就清楚了。使用systemtap监控skb的释放点并打印backtrace,即可快速找到引起丢包的内核函数。Systemtap脚本如图2-1,2-2所示。
    8bbed8831ca7ac10160556d0fcf92360.png图2-1 dropwatch脚本(不带backtrce打印)
    61cf6b33b261778479a205cd73b041d3.png图2-2 dropwatch脚本(带backtrce打印)首先通过图2-1脚本找到丢包点的具体函数,然后找到丢包具体的地址(交叉运行stap --all-modules dropwatch.stp -g和stap dropwatch.stp -g命令,结合/proc/kallsyms里面函数的具体地址),再把丢包地址作为判断条件,精确打印丢包点的backtrace(图2-2)。运行脚本stap --all-modules dropwatch.stp -g,开始复现问题,脚本打印如图2-3:b9cce0ba455f48bc5d19a4b39ebdefd0.png图2-3 丢包函数正常不卡顿的时候是没有nf_hook_slow的,当出现卡顿的时候,nf_hook_slow出现在屏幕中,基本确定丢包点在这个函数里面。但是有很多路径能到达这个函数,需要打印backtrace确定调用关系。再次运行脚本:stap dropwatch.stp -g,确认丢包地址列表,对比/proc/kallsyms符号表ffffffff8155c8b0 T nf_hook_slow,找到最接近0xffffffff8155c8b0 的那个值0xffffffff8155c9a3就是我们要的丢包点地址(具体内核版本和运行环境有差异)。加上丢包点的backtrace,再次复现问题,屏幕出现图2-4打印。
    b778aa9e5c0d4a3bf8bdf270a11eea7e.png图2-4 丢包点backtrace
    d7266a9176d1eeb9a9bba0b9fb9e9b8d.png图2-5连接表状态可以看出ip_forward调用nf_hook_slow最终丢包。很明显数据包被iptable上的FORWARD 链规则丢了。查看FORWARD链上的规则,确实有丢包逻辑(-j REJECT --reject-with icmp-port-unreachable),并且丢包的时候一定会发 icmp-port-unreachable类型的控制报文。到此基本确定原因了。因为是在Node上产生的icmp回馈信息,所以在抓包的时候无法通过Client和Server的地址过滤出这种报文(源地址是Node eth0地址,目的地址是Server的地址)。同时运行systamp脚本和tcpdump工具抓取icmp-port-unreachable报文,卡顿的时候两者都有体现。接下来分析为什么好端端的连接传输了一段数据,后续的数据被规则丢了。仔细查看iptalbe规则发现客户配置的防火墙规则是依赖状态的:-m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT。只有ESTABLISHED连接状态的数据包才会被放行,如果在数据传输过程中,连接状态发生变化,后续入方向的报文都会被丢弃,并返回端口不可达。通过conntrack工具监测连接表状态,发现出问题时,对应连接的状态先变成了FIN_WAIT,最后变成了CLOSE_WAIT(图2-5)。通过抓包确认,GIT在下载数据的时候,会开启两个TCP连接,有一个连接在过一段时间后,Server端会主动发起fin包,而Client端因为还有数据等待传输,不会立即发送fin包,此后连接状态就会很快发生如下切换:ESTABLISHED(Server fin)->FIN_WAIT(Client ack)->CLOSE_WAIT所以后续的包就过不了防火墙规则了(猜测GIT协议有一个控制通道,一个数据通道,数据通道依赖控制通道,控制通道状态切换与防火墙规则冲突导致控制通道异常,数据通道也跟着异常。等有时间再研究下GIT数据传输相关协议)。这说明iptables的有状态的防火墙规则没有处理好这种半关闭状态的连接,只要一方(此场景的Server端)主动CLOSE连接以后,后续的连接状态都过不了规则(-m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT)。明白其中原理以后,对应的解决方案也比较容易想到。因为客户是多租户容器场景,只放开了Pod主动访问的部分服务地址,这些服务地址不能主动连接Pod。了解到GIT以及SVN都是内部服务,安全性可控,让用户把这些服务地址的入方向放行,这样即使状态发生切换,因为满足入向放行规则,也能过防火墙规则。3. 思考

    在排查问题的过程中,发现其实容器的网络环境还有非常多值得优化和改进的地方的,比如:
    • TCP接受发送buffer的大小一般是在内核启动的时候根据实际物理内存计算的一个合理值,但是到了容器场景,直接继承了Node上的默认值,明显是非常不合理的。其他系统资源配额也有类似问题。
    • 网卡的TSO,GSO特性原本设计是为了优化终端协议栈处理性能的,但是在容器网络场景,Node的身份到底是属于网关还是终端?属于网关的话那做这个优化有没有其他副作用(数据包被多个设备buffer然后集中发出)。从Pod的角度看,Node在一定意义上属于网关的身份,如何扮演好终端和网关双重角色是一个比较有意思的问题
    • Iptables相关问题
    此场景中的防火墙状态问题规则多了以后iptables规则同步慢问题Service 负载均衡相关问题(规则加载慢,调度算法单一,无健康检查,无会话保持,CPS低问题)SNAT源端口冲突问题,SNAT源端口耗尽问题
    • IPVS相关问题
    统计timer在配置量过大时导致CPU软中断收包延时问题net.ipv4.vs.conn_reuse_mode导致的一系列问题 (参考:https://github.com/kubernetes/kubernetes/issues/81775 )截止到现在,以上大多数问题已经在TKE平台得到解决,部分修复patch提到了内核社区,相应的解决方案也共享到了K8s社区。END
    Kubernetes CKA实战培训班推荐:

    北京站:9月11-13日

    上海站:9月18-20日

    be50c1f55d35564b5a2e5a31bd14dad0.png

    bf0c22e994858eaaba5dbe8aa5822534.gif

    4d31406b10267c847f967fe97ca7745a.png

    展开全文
  • 煤矿机械设备参数变化规律主要体现在煤矿机械设备技术参数监测...首先介绍了人工神经元模型、神经网络学习方法以及动态仿真等相关理论知识,在此基础上对基于神经网络的煤矿机械设备状态监测记录模型具体应用进行阐述。
  • 关于监听网络状态变化,记录而已

    千次阅读 2015-08-24 11:07:49
    在我们平常开发中,有很多场景需要监听网络状态的变化。今天,我们来实现该功能。大致效果如下: <!-- ---------------------卖萌的分割线--------------------- -->首先我们先看一下大概Demo结构: 接下来,贴...

    在我们平常开发中,有很多场景需要监听网络状态的变化。今天,我们来实现该功能。大致效果如下:
    这里写图片描述

    <!-- ---------------------卖萌的分割线--------------------- -->

    首先我们先看一下大概Demo结构:
    包结构

    既然涉及到网络,因此我们需要在AndroidManifest文件中添加以下权限:

     <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
     <uses-permission android:name="android.permission.INTERNET"/>

    接下来,贴一下NetUtils类的代码,该类主要用于判断目前网络状态,代码不复杂,直接上代码:

    package network;
    
    import android.content.Context;
    import android.net.ConnectivityManager;
    import android.net.NetworkInfo;
    
    public class NetUtils {
    
        // 判断网络连接状态
        public static boolean isNetworkConnected(Context context) {
            if (context != null) {
                ConnectivityManager mConnectivityManager = (ConnectivityManager) context
                        .getSystemService(Context.CONNECTIVITY_SERVICE);
                NetworkInfo mNetworkInfo = mConnectivityManager
                        .getActiveNetworkInfo();
                if (mNetworkInfo != null) {
                    return mNetworkInfo.isAvailable();
                }
            }
            return false;
        }
    
        // 判断wifi状态
        public static boolean isWifiConnected(Context context) {
            if (context != null) {
                ConnectivityManager mConnectivityManager = (ConnectivityManager) context
                        .getSystemService(Context.CONNECTIVITY_SERVICE);
                NetworkInfo mWiFiNetworkInfo = mConnectivityManager
                        .getNetworkInfo(ConnectivityManager.TYPE_WIFI);
                if (mWiFiNetworkInfo != null) {
                    return mWiFiNetworkInfo.isAvailable();
                }
            }
            return false;
        }
    
        // 判断移动网络
        public static boolean isMobileConnected(Context context) {
            if (context != null) {
                ConnectivityManager mConnectivityManager = (ConnectivityManager) context
                        .getSystemService(Context.CONNECTIVITY_SERVICE);
                NetworkInfo mMobileNetworkInfo = mConnectivityManager
                        .getNetworkInfo(ConnectivityManager.TYPE_MOBILE);
                if (mMobileNetworkInfo != null) {
                    return mMobileNetworkInfo.isAvailable();
                }
            }
            return false;
        }
    
        // 获取连接类型
        public static int getConnectedType(Context context) {
            if (context != null) {
                ConnectivityManager mConnectivityManager = (ConnectivityManager) context
                        .getSystemService(Context.CONNECTIVITY_SERVICE);
                NetworkInfo mNetworkInfo = mConnectivityManager
                        .getActiveNetworkInfo();
                if (mNetworkInfo != null && mNetworkInfo.isAvailable()) {
                    return mNetworkInfo.getType();
                }
            }
            return -1;
        }
    }
    

    接下来是NetReceiver类,该类是广播接收器,用于接收网络状态变化的广播,直接贴代码:

    package receiver;
    
    import interf.IChangeTextCallback;
    import network.NetUtils;
    import android.content.BroadcastReceiver;
    import android.content.Context;
    import android.content.Intent;
    import android.net.ConnectivityManager;
    
    public class NetReceiver extends BroadcastReceiver {
    
        private IChangeTextCallback mCallback;
    
        public NetReceiver(IChangeTextCallback callback) {
            this.mCallback = callback;
        }
    
        @Override
        public void onReceive(Context context, Intent intent) {
            String action = intent.getAction();
            if (ConnectivityManager.CONNECTIVITY_ACTION.equals(action)) {
                boolean isConnected = NetUtils.isNetworkConnected(context);
                System.out.println("网络状态:" + isConnected);
                System.out.println("wifi状态:" + NetUtils.isWifiConnected(context));
                System.out.println("移动网络状态:" + NetUtils.isMobileConnected(context));
                System.out.println("网络连接类型:" + NetUtils.getConnectedType(context));
                /*
                 * if (isConnected) { Toast.makeText(context, "已经连接网络",
                 * Toast.LENGTH_LONG).show(); } else { Toast.makeText(context,
                 * "已经断开网络", Toast.LENGTH_LONG).show(); }
                 */
                if (NetUtils.isWifiConnected(context)) {
                    mCallback.setText("wifi");
                } else if (NetUtils.isMobileConnected(context)) {
                    mCallback.setText("移动网络");
                } else if (!isConnected) {
                    mCallback.setText("无网络");
                }
            }
        }
    
    }
    

    接下来是MainActivity,该Activity布局就只是一个简单的TextView,我们在这里实现了IChangeTextCallback回调接口,用于传入上面的Receiver回调更改Activity的UI。代码如下:

    package com.example.nettest;
    
    import interf.IChangeTextCallback;
    import receiver.NetReceiver;
    import android.app.Activity;
    import android.content.IntentFilter;
    import android.net.ConnectivityManager;
    import android.os.Bundle;
    import android.widget.TextView;
    
    public class MainActivity extends Activity implements IChangeTextCallback {
    
        NetReceiver mReceiver = new NetReceiver(this);
        IntentFilter mFilter = new IntentFilter();
        private TextView mTextview;
    
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
    
            mTextview = (TextView) this.findViewById(R.id.text);
    
            mFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
            registerReceiver(mReceiver, mFilter);
        }
    
        @Override
        protected void onDestroy() {
            unregisterReceiver(mReceiver);
            super.onDestroy();
        }
    
        @Override
        public void setText(String text) {
            mTextview.setText(text);
        }
    }
    

    最后是IChangeTextCallback回调接口,很简单就一行代码:

    package interf;
    
    public interface IChangeTextCallback {
        public void setText(String text);
    }

    这样 ,我们就实现了Android对网络状态的实时监听以及做出相对应的操作。

    展开全文
  • ubuntu即使可以上网,网络状态图标依然显示未连接,解决办法: vi /etc/NetworkManager/NetworkManager.conf sudo service network-manager restart 在进入配置文件后,将managed项改成true,wq保存退出之后,...

    ubuntu即使可以上网,网络状态图标依然显示未连接,解决办法:

    vi /etc/NetworkManager/NetworkManager.conf
    sudo service network-manager restart

    在进入配置文件后,将managed项改成true,wq保存退出之后,重启服务就可以了。

    展开全文
  • 本文分享了iptable防火墙状态异常导致丢包的排查记录,这个排查过程非常曲折,最后使用了在现在的作者看来非常落伍的工具:systemtap,才得以排查成功。其实依作者现有的经验,此问题现在仅需一条命令即可找到原因,...
  • 一些常见的状态码为: 200- 服务器成功返回网页404- 请求的网页不存在503- 服务不可用 所有状态解释:点击查看 1xx(临时响应) 表示临时响应并需要请求者继续执行操作的状态代码。 代码 说明 100 (继续) ...
  • 开发遇到的网络判断思路: 不能每次网络请求都要去调用ConnectivityManager进行网络判断,所以在程序启动的时候判断一次网络状态,然后全局记录这个状态,每次网络请求的时候只用根据这个记录的状态来判断网络的...
  • 本文分享了iptable防火墙状态异常导致丢包的排查记录,这个排查过程非常曲折,最后使用了在现在的作者看来非常落伍的工具:systemtap,才得以排查成功。其实依作者现有的经验,此问题现在仅需一条命令即可找到原因,...
  • 网络状态检查工具类

    2019-12-04 15:43:05
    网络状态检查工具类,做个记录方便以后使用 package com.wjy.myokhttp.net; import android.content.Context; import android.content.Intent; import android.net.ConnectivityManager; import android.net....
  • 自“净网2019”专项行动开展以来,平罗县公安局网安大队积极行动,对全县重要网站及互联网运营单位开展网络安全监督...未严格采取监测、记录网络运行状态网络安全事件的技术措施;未执行网络安全等级保护制度;未...
  • 关于进程: ps 查询当前终端下运行的进程 ps aux 查看系统里所有的进程,前台的,后台的 USER 进程的用户 PID 进程的ID VSZ 虚拟内存大小 RSS 物理内存大小 ...STAT 状态。... S休眠状态 ...
  • 1、引言媒体发展已经步入融媒体时代,...其内容涵盖播出信号、转播的外来信号源(央广卫星信号、央广微波信号、有线网络信号、本地电视频道信号等)、传输发射覆盖回收信号。系统依靠计算机监测与控制技术、多媒体监测...
  • 根据上级部门有关工作部署,玉林市...检查中,检查组成员认真听取了责任单位网络信息安全工作汇报,详细了解各单位关于国家网络安全等级保护制度、网络安全技术防护措施和安全管理制度、制定网络安全事件应急预案、...
  •   对于移动端来说,基本上大多数数据都是来自于网络端的数据传输...另多记录一句,在21版本时加入了NetworkCallback类来监听网络状态的变化,官方提议在28及以上通过NetworkCallback的方式来监听网络,但实际中目前还
  • 对用户登录状态的监听,可以分为前端和后端两个方向去做,我们也从这两个方面分析一下。 前端 去调用一个userInfo的身份请求,当用户登录了,userInfo请求必然有相应的用户信息。 后端 将所有接口的访问结果做成...
  • 用来写result结果,只有网络异常的时候才会输出 def write_resules(filename,results): try : file = open(filename, " a " ) file.write(time.asctime(time.localtime(time.time())) + " : " + ...
  • android 网络状态判断

    2014-04-21 10:09:00
    许多联网应用都在开始运行的时候检查当前网络状态,如果没有开启则去开启它,记录一下以前写程序时的网络检查,发现人的记忆力真是有限,总是隔段时间久忘记,所以记录下来是最好的记忆。 我们可以在一开始启动程序...
  • LSTM网络学习记录

    2020-06-28 09:37:54
    因此就有了循环神经网络,将上一时刻得状态引入到当前时刻,但随着网络深度得增加,不可避免的受到了梯度消失核梯度爆炸得诅咒。因此就有人整出了LSTM,它通过遗忘门选择丢弃掉哪些信息,通过输入门选择更新哪些信息...
  • 本人最近由于要管理很多终端,有时候终端死机,网络不通,于是乎写了一个监控程序,c#+xml多线程测试Ip是否ping通,然后记录日志,查询状态,增、删、改、查Ip和对应位置信息,可以最小化到托盘,回车添加记录,要想...
  • 推荐单位:葛洲坝水力发电厂本文作者:高劲、松杜波、桑希涛摘要:本文介绍了葛洲坝智能电站建设对励磁系统的技术要求,提出了励磁系统智能化、网络化设计的总体思路, 介绍和分析了励磁系统智能化在线监测的方式、...
  • 公司的APP中需要程序随时注意网络状态的变化,一旦变化就要弹框提醒,这可愁坏了他,于是让我帮忙找一下相关的方法。这里我就贴出来对应的方法供大家使用,同时也作为自己的一份记录。 获取当前网络状态,这个我们...
  • 安卓中判断网络状态

    2017-12-14 03:50:13
    前言 最近整理公司的项目,思考...需要获取当前手机的网络状态,包括: 当前网络是否可用? 当前网络是WiFi网络吗? 当前网络是移动网络吗? 当前WiFi是否打开? 解决 关于第一个问题,代码如下: /** * 判断网...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,905
精华内容 1,162
关键字:

网络状态记录