netstat awk统计网络中连接状态

通过结合netstat命令和awk工具,可以方便地统计服务器上不同TCP连接状态的数量。文章介绍了如何利用awk的字符匹配功能来实现这一统计过程,并提供了一个简单的awk命令示例,解释了命令的工作原理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

利用awk字符匹配处理 统计网络中tcp连接状态

在服务器的维护过程中经常涉及到网络连接状态的统计。netstat 与 awk 配合可轻松做到统计功能。
netstat -n 可以打印网络连接的详细信息
这里写图片描述
可以看到在state列包含状态信息,如果说想统计每种连接状态的数量得到这样的一种统计结果

ESTABLISHED 7
SYN_SENT 2

我们可以用数的, 1 2 3 4…(开个玩笑,当成千上万的连接出现时会疯掉, 本着脚本至上的理念还是用命令的好), 通常的统计命令如下:

netstat -n | awk '/^tcp/ {++State[$NF]} END {
   
   for (i in State) print i, State[i]}'

但貌似有些晦涩难懂,我们可以man awk查看一下awk的帮助文档

SYNOPSIS
       awk [ -F fs ] [ -v var=value ] [ 
<think>我们被要求使用netstat命令在Shell中查看网络连接状态的数量,并按照连接数降序输出。 根据引用[4]中的示例,我们需要统计各个状态的连接数,并降序输出。 我们可以使用以下步骤: 1. 使用netstat命令(通常需要root权限来查看所有连接)来获取所有连接,特别是TCP连接的状态。 2. 使用grep等工具提取出状态行。 3. 使用awk或cut等工具分割出状态列。 4. 使用sort和uniq等工具进行统计和排序。 但是注意,引用[4]中给出的示例输出是: ESTABLISHED 22 TIME_WAIT 9 LISTEN 3 因此,我们可以设计如下命令: 命令分解: a. 使用netstat -ant:显示所有TCP连接(-a表示所有,-n表示数字形式,-t表示TCP,但通常我们也会包括UDP?不过题目要求TCP连接,引用[4]中也是tcp连接) b. 使用grep 'tcp':过滤出tcp的行(因为netstat -ant输出的都是tcp,但有时也会包含udp?所以这里我们明确用'tcp'过滤,但注意netstat输出中协议列是tcp) c. 使用awk '{print $6}':提取状态列(在netstat的输出中,状态是第6列,但注意不同系统可能列数不同?在Linux中,通常输出格式为:Proto Recv-Q Send-Q Local Address Foreign Address State,所以状态是第6列) d. 对状态进行排序(因为uniq -c要求相邻) e. 使用uniq -c:统计每个状态出现的次数 f. 再次按出现次数降序排序:sort -nr 但是注意:有些连接状态可能为空(比如LISTEN状态的行,状态在第6列,但其他行呢?)。另外,我们可能要去掉第一行标题(但netstat通常不会在非交互式输出标题?) 然而,在引用[4]中,他们使用了一个shell脚本来实现,并且输出格式是状态和数量。 因此,我们可以写出如下命令: netstat -ant | grep 'tcp' | awk '{print $6}' | sort | uniq -c | sort -rn | awk '{print $2, $1}' 解释: 1. netstat -ant:显示所有TCP连接(不解析主机名) 2. grep 'tcp':过滤出包含tcp的行(实际上netstat -ant输出的每一行都有tcp,所以也可以省略,但为了确保,保留) 3. awk '{print $6}':打印第6列(状态) 4. sort:排序,使相同状态相邻 5. uniq -c:统计每个状态出现的次数,输出格式为“数量 状态” 6. sort -rn:按数量(第一列)数值降序排序 7. 再用awk将两列位置互换:因为uniq -c输出的格式是“数量 状态”,而我们需要“状态 数量”,所以用awk '{print $2, $1}' 但是注意:有些状态可能是空,比如标题行?我们可以用grep过滤掉空行,或者过滤掉标题行。另外,标题行中第6列是“State”,我们可以用grep -v 'State'来排除。 因此,改进: netstat -ant | awk '/^tcp/ {print $6}' | sort | uniq -c | sort -rn | awk '{print $2, $1}' 这里使用awk只处理以tcp开头的行(即协议是tcp的行),这样就去除了标题行(标题行通常不以tcp开头,而是以Proto开头)和udp行(如果有的话)。 但是注意:在有些系统中,标题行可能是英文,我们使用/^tcp/匹配以tcp开头的行,自然就排除了标题行。 另外,也可以使用: netstat -ant | tail -n +3 | awk '{print $6}' | ... # tail -n +3 表示从第3行开始(跳过前两行),但不同系统输出行数可能不同,所以不推荐。 所以,我们采用awk过滤以tcp开头的行。 但是,注意:有些连接状态可能是空?比如,在LISTEN状态时,第6列是LISTEN,但有些状态可能没有?实际上,TCP连接的状态都在第6列。 因此,我们使用上述命令。 但是,注意:在有些系统中,netstat输出可能有不同的列数,比如当使用-p选项时,会多出一列。但我们这里没有使用-p,所以列数是固定的。 另外,引用[4]中的题目要求是编写shell脚本,输出格式为:状态 数量,且降序。 示例输出: ESTABLISHED 22 TIME_WAIT 9 LISTEN 3 所以,我们按照这个命令即可。 但是,为了确保在大多数Linux系统上可用,我们可以测试一下。 另外,我们也可以使用ss命令(更现代的工具)来实现,但题目要求netstat。 因此,最终命令: netstat -ant | awk '/^tcp/ {print $6}' | sort | uniq -c | sort -rn | awk '{print $2, $1}' 注意:如果状态列不是第6列,需要调整。我们可以先运行netstat -ant看一下输出格式。 例如,在我的系统上(Ubuntu)运行netstat -ant的输出示例: Active Internet connections (servers and established) Proto Recv-Q Send-Q Local Address Foreign Address State tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN tcp 0 0 127.0.0.1:5432 0.0.0.0:* LISTEN tcp 0 52 192.168.1.100:22 192.168.1.101:65432 ESTABLISHED 所以,第一行是标题,第二行开始每行以tcp开头,状态在第6列。 因此,上述命令是可行的。 另外,引用[4]中给出的解决方案可能类似,但他们的示例输出中状态都是大写的,而我们的输出也是大写的,所以没问题。 但是,注意:有些状态可能是小写?不会,netstat输出状态都是大写。 所以,我们给出这个命令。 另外,如果用户没有root权限,可能无法看到其他用户的进程连接,但统计状态还是可以统计到当前用户可见的连接。 如果用户需要查看所有连接(包括其他用户的),则需要sudo。 因此,我们可以建议用户使用sudo来运行,以确保看到所有连接。 但是,题目没有要求,所以我们可以不写。 因此,最终回答:</think>### 使用 netstat 统计网络连接状态数量 要查看系统 TCP 连接中各状态的数量并按连接数降序输出,可通过以下命令组合实现: ```bash netstat -ant | awk '/^tcp/ {print $6}' | sort | uniq -c | sort -rn | awk '{print $2, $1}' ``` #### 命令详解: 1. **`netstat -ant`** - `-a`:显示所有连接 - `-n`:禁用域名解析(显示 IP 和端口号) - `-t`:仅显示 TCP 连接 - 输出示例: ```bash tcp 0 0 192.168.1.10:22 203.0.113.5:54321 ESTABLISHED tcp 0 0 0.0.0.0:80 0.0.0.0:* LISTEN ``` 2. **`awk '/^tcp/ {print $6}'`** - 过滤以 `tcp` 开头的行,提取第 6 列(状态列) - 输出:`ESTABLISHED`、`LISTEN` 等状态值[^3] 3. **`sort | uniq -c`** - 对状态排序后统计每种状态的数量 - 输出示例: ```bash 22 ESTABLISHED 9 TIME_WAIT 3 LISTEN ``` 4. **`sort -rn | awk '{print $2, $1}'`** - `sort -rn`:按数量降序排序 - `awk`:调整输出格式为 `状态 数量` - 最终输出: ```bash ESTABLISHED 22 TIME_WAIT 9 LISTEN 3 ``` #### 扩展用法: - **包含 UDP 连接**: ```bash netstat -anu | awk '/^udp/ {print $1}' | sort | uniq -c | sort -rn ``` - **实时监控连接状态变化**: ```bash watch -n 1 "netstat -ant | awk '/^tcp/ {print \$6}' | sort | uniq -c" ``` - **仅统计特定状态(如 TIME_WAIT)**: ```bash netstat -ant | grep -c 'TIME_WAIT' ``` #### 输出字段说明: | 状态 | 含义 | 常见场景 | |---------------|--------------------------|------------------------| | `ESTABLISHED` | 连接已建立 | 正常数据传输中 | | `TIME_WAIT` | 等待关闭 | 主动关闭连接后残留状态 | | `LISTEN` | 端口监听中 | 服务等待连接 | | `SYN_SENT` | 发起连接请求(握手阶段) | 客户端连接服务器时 | > ⚠️ 注意:查看进程信息需 root 权限,建议使用 `sudo netstat -antp`[^5]。 --- ### 典型应用场景 1. **服务器监控**: ```bash # 检查高并发场景下的连接状态 netstat -ant | awk '/^tcp/ {print $6}' | sort | uniq -c ``` - `TIME_WAIT` 过多可能耗尽端口资源,需优化内核参数[^1] 2. **安全审计**: ```bash # 检测异常连接状态 netstat -ant | grep -E 'SYN_RECV|CLOSE_WAIT' | wc -l ``` - `SYN_RECV` 突增可能遭遇 SYN Flood 攻击 3. **服务可用性检查**: ```bash # 验证 Web 服务是否监听 netstat -ant | grep ':80 .*LISTEN' | wc -l ``` ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值