平时在Android/Ubuntu这样的Linux系统中, 经常跟网络打交道, 不可避免的要使用网络工具来定位问题;这里对Linux常用的网络工具进行简单的总结, 方便后续查阅使用. 主要看看以下几个常用的网络工具:
- ping: 基于ICMP协议, 发送ICMP数据包用于测试网络连通状态
- traceroute: 基于UDP/ICMP/TCP协议用于跟踪网络连通状态, 打印达到目标地址的路由信息
- tcpdump : 用于抓取tcp/ip包, 分析网络问题的必需神器
- iproute2 : 查看/添加/删除当前路由信息
- netstat: 查看网络状态
- netcfg: 配置网口(使能网口以及配置IP等)
- iptables: 网络数据包的过滤以及防火墙策略配置
- netcat: 用于快速建立TCP/UDP链接,检测网络的连通性
- iperf: 网络性能测试工具, 用来衡量网络吞吐量/带宽
- tc: Traffic Control, 用于显示/修改网卡配置的工具
- curl: 基于libcurl的数据传输工具, 支持HTTP/HTTPS/FTP/RTMP/RTSP/SCP等常见协议
- iw: 用于显示/设置WiFi设备接口的工具, 比如展示当前设备WiFi热点信息, 主动扫描周围WiFi热点等
- ethtool: 查看/设置以太网网卡驱动/硬件配置
ping
ping通过向目标节点发送ICMP的ECHO_REQUEST
包来测试目标地址的可达性与连通性;向目标地址发送ECHO_REQUEST
包后, 如果正常接收到ECHO_RESPONSE
, 则说明网络是连通的; 但如果没有接收到任何回应,并不能说明网络的不通, 有可能是请求或者响应在某个地方丢失了.通过ping的洪峰测试模式, 持续发包到目标地址, 也可以查看当前网络状态, 如RTT(Round-trip time)时间, 网络的丢包率等信息.
一般测试中常用的参数有如下几个:
-c
: 设置发多少个ECHO_REQUEST
包-i
: 两个包之间的时间间隔, 默认是1s-I
: 指定数据包出去的端口-w
: ping测试的超时时间, 多久结束-f
: 洪峰测试, 持续(两个包的时间间隔为0)向目标主机发送数据包-s
: 指定发送数据包的大小-M
: 选择Path MTU发现策略, 有三个选择:do
代表不要对数据包进行分片,want
表示执行PMTU发现, 但是可以在本地进行数据包的分片,
dont
表示不要设置分片标志位(可以分片)
示例: 向某个域名发送10包,
1 |
|
持续向某个主机连续20s发送数据包, 并指定出口为wlp5s0
:
1 |
|
通过指定包大小以及PMTU的策略,可以用来发现某个路径上最大的MTU大概是多少:
1 |
|
一般, ping测试完成后, 会打印发生了多少个包, 接收的包个数以及丢包率, 总的测试时间以及RTT:
traceroute
traceroute能够跟踪打印通往某个网络主机的路由信息, 用于定位网络不通时,在哪个路由节点发生的异常. traceroute利用的是IP协议中的包的TTL(Time-To-Live)字段不断发送”探针”包;其首先会向网络发送一个TTL为1的包, 返回后接着向网络发送一个TTL为2的包, 以此持续发送, 直到最后到达目标主机或者超时为止.traceroute的参数较多, 可以通过man traceroute
或者traceroute --help
查看具体的用法.
示例, 查找到达www.google.com
的路由:
1 |
|
tcpdump
tcpdump用于抓取网络数据包的利器, 最初的版本是由Van Jacobson, Sally Floyd, Vern Paxson在1988年编码, 后来在各种操作系统中都得到了广泛的使用, 更多详细信息可以参考https://www.tcpdump.org/;如果你使用的是Linux系统, 可以通过man tcpdump
来查看tcpdump的具体使用信息. 这里来看下Linux下的tcpdump工具具体如何使用.
以Ubuntu系统为例, tcpdump有很多参数:
常用的参数主要有如下几个:
-i *interface*/--interface=*interface*
: 设置需要抓包的网口, 在Ubuntu系统可以通过ifconfig
查看每个网络接口信息; 在Android下可以通过busybox ifconfig
查看;-n
: 不要将IP地址转换成域名;-s *snaplen*/ --snapshot--length=*snaplen*
: 为了保持兼容性, 一般将该值设为0;-w *file*
: 保存网络数据包到某个文件;expression
: 表达式, 由于网络数据包的过滤, 关于表达式的语法格式可以参考man pcap-filter
;
示例: 比如我要抓取某个端口wlp5s0
上的所有数据包, 可以使用:
1 |
|
如果只是想看某个端口指定一个协议, 如tcp的数据包, 则可以:
1 |
|
这里ip proto \\tcp
就是包过滤的表达式, 具体的写法可以参考man pcap-filter
或者http://alumni.cs.ucr.edu/~marios/ethereal-tcpdump.pdf
iproute2
看名字大概也知道iproute2
这个是用来管理linux系统路由表的, 但在这个工具系列中其实也集成了其他有用的功能, 比如地址/链路的管理, 查看ARP信息, 配置网络接口信息以及配置策略路由(policy routing)等(man ip
查看对应信息), 对于Ubuntu系统可以通过man ip-route
来查看如何使用iproute
:
示例: 想看下系统的路由表,
1 |
|
如果想要看某个具体的路由表信息:
1 |
|
那么, 如果要在某个路由表中添加一项路由信息, 如何操作?假定现在, 需要在main
路由表中对应的端口ppp0
中添加一个目标ip为211.137.20.302
的路由:
1 |
|
想要删除路由表中的某一项, 语法跟路由表添加很相似:
1 |
|
在某个网口上添加默认路由:
1 | ip route add default proto static scope link dev wlp5s0 |
netstat
netstat主要用来看路由表, 当前网络链接状态以及网络数据统计等, 最新的Linux系统已经使用ip
(man ip
)来替代(具体的信息可以通过man netstat
查看).不过在Android的busybox中仍然可以发挥作用:
例如输入adb shell busybox netstat -rn
显示路由表:
netcfg
在Ubuntu系统中并没有看到netcfg
工具(对应的一个工具是ifconfig
), Android里边有一个netcfg
工具用于配置网口:
1 |
|
通过ADB命令adb shell netcfg
可以查看当前网口的配置:
如果要在Android中配置一个以太网口(Ethernet), 确保驱动加载完成后, 输入以下指令即可:
- 使能网口
1 |
|
- 通过DHCP获取IP地址
1 |
|
查看与配置网卡的另外一个工具是ifconfig
, 相比netcfg
, ifconfig
提供更多的功能选项, 具体可以参考man ifconfig
.
iptables
iptables是Linux内核模块netfilter(https://www.netfilter.org/)在用户空间的工具, 可以对网络数据包进行转发, 拦截, 过滤以及修改. 简单说来, netfilter是在tcp/ip的内核传输路径添加各种hooks函数(chains),如PREROUTING
, INPUT
, FORWARD
, OUTPUT
, POSTROUTING
; 这些hooks函数负责将数据包发送个各个队列(tables), 示意图如下:
PREROUTING
: 对应NF_IP_PRE_ROUTING
hook函数, 从外部节点发送到网卡的数据在进入协议栈之前会在该hook处理INPUT
: 对应NF_IP_LOCAL_IN
hook节点, 协议栈对数据做了路由处理, 确认数据包是发送到当前系统的会在这里处理FORWARD
: 对应NF_IP_FORWARD
hook函数, 协议栈做了路由处理, 确认该数据是转发给其他节点的包会在该hook函数处理OUTPUT
: 对应NF_IP_LOCAL_OUT
hook函数, 所有本地进程的数据包在进入协议栈之后会在该hook函数处理POSTROUTING
: 对应NF_IP_POST_ROUTING
hook函数, 数据被协议栈做了路由处理, 在进入网卡之前会在该hook函数处理
在Linux中内置的tables有如下几个:
- Filter: 用于数据包过滤(接收或者丢弃), 只有
INPUT
/FORWARD
/OUTPUT
实现filter
表 - Nat: IP地址转换, 有源地址(snat), 目标地址(dnat)以及masquerade(装饰)三种, SNAT实现的节点有
INPUT
,POSTROUTING
; DNAT实现的节点PREROUTING
/OUTPUT
- Managle: 修改数据包的头(ttl/tos等), mangle表在所有hook节点都有实现
- Raw: 主要用于配置链接跟踪(connection tracking),
PREOUTING
/OUTPUT
节点实现了raw
表
有关iptables使用的具体示例可以参考Linux Configuration for NAT and Firewall在Ubuntu系统中, 输入man iptables
可以查看iptables的具体用法:
比如要查看当前iptables规则, 可以通过iptables --list
; 一般iptables
命令有如下几个部分组成:
假定你现在需要拦截所有来自某个IP地址的数据包, 可以这样操作:
1 |
|
如果只是想丢弃某种协议的数据包, 比如UDP, 则可以指定协议类型:
1 |
|
查看当前规则的流量使用情况可以使用:
1 |
|
通过iptables的规则链条, 我们可以很方便的构造一系列防火墙规则, 是一个非常强大的工具, 值得学习; Linux内核netfilter数据过滤规则可以参考Wikipedia中详细的流程图, 从中我们可以看到内核中不同规则链上上规则的适用情况.
netcat
netcat
通常简写成nc
, 是一个用于建立TCP/UDP连接的小工具, 在Linux下netcat -h
或者nc -h
都可以查看其使用说明;Android也包含了一个缩减版的netcat
, 可以通过nc -h
查看. 以Ubuntu为例, 通常nc
有如下几个参数:
比如要测试下跟google的TCP连接是否正常(设置-v
可以输出连接的状态信息):
1 |
|
类似的, 也可以建立一个UDP连接:
1 | nc -v -u www.google.com 80 |
netcat
有个比较有用的功能就是扫描某个主机给定范围的端口是否正常可连接: 如下这个指令用来查看网关192.168.225.1
上1-10000
的端口是否可用
1 |
|
如果我们想要测试两个主机给定端口的连通性,可以按照如下步骤操作:
1 |
|
关于nc
更多有趣的应用, 可以到官网上查看 http://nc110.sourceforge.net/.
iperf
iperf
是一个基于TCP/UPD协议的网络测试工具, 常用来测试网络吞吐量以及带宽. 在测试时需要客户端与服务端都支持. 目前有iperf3/iperf2两个版本, 相关文档参考https://iperf.fr/iperf-doc.php. 这里我们基于iperf2介绍下如何来使用iperf.
iPerf的参数主要分为三类, 一类是通用参数, 如参数格式, 多线程测试等;一类是客户端使用的参数, 如目标地址;一类是服务端的参数, 如基于UDP或者通过Daemon进程执行等.
比如简单来测试下网络带宽(ping.online.net
是免费用来测试网络的服务器):
1 |
|
测试完成后, 会输出如下信息:
这里只是简单引出iperf的使用方法, 更多使用场景可以到官网上看看文档https://iperf.fr/.
tc
tc即Traffic Control
, 可以显示/修改网卡的配置, 如设置网卡的延时, 传输速率, 控制包的传输顺序等, 在linux上输入man tc
可以查看具体的使用说明:
比如要看下当前网卡队列的状态, 可以输入:
1 |
|
curl
curl
一般用于客户端数据的下载传输, 目前支持Web协议如HTTP(S)/FTP到视频流传输协议如RTMP/RTSP等, 其使用起来也非常简单:
1 | curl [options...] <url> |
比如要尝试下载某个网页:
1 |
|
这里-v
会输出更多的过程信息:
iw
iw
常用于WiFi设备的管理, 配置, 通过man iw
可以看到相关的使用说明:
要查看所有相关命令的使用可以输入iw help
.如要查看当前设备WiFi信息, 可以输入iw dev
. 通过:
1 |
|
可以查看到当前连接的WiFi热点信息, 如果要扫描附近的WiFi热点, 可以通过iw <wlan_interface> scan
, 这样会得到一个完整的热点列表.
ethtool
ethtool
可以用来查看/设定以太网网卡的驱动以及硬件配置, 是以太网驱动开发调试的利器, 其可以用来查看/配置网卡环形缓冲区大小, 可以查看/配置网卡的各种特性(如各种offload开关, 中断合并(Interrupt coalescing
)等), 可以通过ethtool -h
查看使用的具体命令:
比如使用ethtool -k eth0
可以查看当前网卡的offload
配置:
1 |
|
如果要修改某个offload
配置, 则使用大写的K
, 如ethtool -K eth0 gso off
可以关闭网卡的GSO
(generic-segmentation-offload
)配置, 具体可以参考man ethtool
中的说明.
以上便是常用几个网络工具的总结了, 大家有什么好的Linux工具可以推荐下~以后持续更新
参考文献
- http://stud.netgroup.uniroma2.it/cgrl/2018/slides/5-netfilter.pdf
- https://en.wikipedia.org/wiki/Netfilter
- https://iperf.fr/(iPerf官网)
- http://linux-ip.net/html/tools-ip-route.html
- https://en.wikipedia.org/wiki/Iptables
- https://linux.die.net/man/8/tc
- https://www.digitalocean.com/community/tutorials/a-deep-dive-into-iptables-and-netfilter-architecture