Linux路由网关下查看客户端IP的实际流量

相信不少朋友都知道,使用Linux搭建路由网关,提供nat上网服务是非常简单的事情,而且性能也不错。但现在p2p的工具很多,有时候带宽会被这些工具在无意中就占满了(例如:使用迅雷、BT下载等)。这时候,总希望看看到底是谁在占用带宽。这样的工具有很多,如ntop、bandwidthd、iftop、IPTraf、MRTG等等,它们也提供了非常方便的图形监控界面,操作也非常简单。可惜,它们都有一些缺点,像实时性不够、IP流量分散、需要使用Web来查看等,恰好这些就是好我需要的。
    为此,我 利用iptables的统计功能 ,编写了一个小脚本来实现要求。(原想用Perl的Net::Pcap模块的对数据包解码统计的,但既然有现成的,为什么不用呢?)O(∩_∩)O哈哈~

一、查看网卡流量
首先,可能我们需要查看的是服务器上总的网卡流量。这个Linux提供了很好的数据:
引用
# cat /proc/net/dev
Inter-|   Receive                                                |  Transmit
face |bytes    packets errs drop fifo frame compressed multicast|bytes    packets errs drop fifo colls carrier compressed
    lo:10020933   79976    0    0    0     0          0         0 10020933   79976    0    0    0     0       0          0
  eth0:3274190272 226746109 438150 858758 369237     0          0         0 2496830239 218418052    0    0    0     0       0          0
  sit0:       0       0    0    0    0     0          0         0        0       0    0    0    0     0       0          0
  tun0:       0       0    0    0    0     0          0         0        0       0    0    0    0     0       0          0
  tun1:    4675      51    0    0    0     0          0         0     8116      48    0    0    0     0       0          0
  tun2:   51960     562    0    0    0     0          0         0   249612    3077    0    0    0     0       0          0
  ppp0:4163571679 12086605    0    0    0     0          0         0 3089285665 15934370    0    0    0     0       0          0

这是网络启动后,通过服务器上各网卡的总流量,但不是很直观。(受排版影响,不太好看)
这里,提供一个小工具:
这工具不是我写的,作者是 。使用非常简单:
引用
# sh flow.sh
Usage: flow.sh <ethernet device> <sleep time>
    e.g. flow.sh eth0 2
# sh flow.sh ppp0 2
IN: 232 KByte/s   OUT: 30 KByte/s
IN: 230 KByte/s   OUT: 38 KByte/s
IN: 241 KByte/s   OUT: 30 KByte/s

给出您要监控的网卡设备,然后是间隔时间,即会告诉您该设备的流量。

二、查看客户端IP实际流量的原理
接下来,进入我们的正题。除了通过上述脚本可以查看到网卡的实际流量外,我们该如何查看每个客户端的单独流量呢?先说说原理吧。
1、iptables设置
该过程最主要的就是利用了iptables的统计功能。
当我们用iptables实现nat转发后,所有的数据包要出去,必须要通过这台网关服务器,也就是说,我们只要在上面监控即可。并且,这些数据包都会经过iptables的FORWARD chain。这时,我们只要给iptables加上下述语句:

# iptables -I FORWARD -s 192.168.228.200 -j ACCEPT
# iptables -I FORWARD -d 192.168.228.200 -j ACCEPT

那么,通过192.168.228.200(客户端)经该服务器路由网关转发出去的数据包就会记录在iptables FORWARD chain中。
如:
引用
# iptables -v -n -x -L FORWARD
Chain FORWARD (policy DROP 5 packets, 351 bytes)
    pkts      bytes target     prot opt in     out     source               destination
2834533  360907743 ACCEPT     all  --  *      *       192.168.228.200      0.0.0.0/0
3509528  3253144061 ACCEPT     all  --  *      *       0.0.0.0/0            192.168.228.200

这样,我们通过一些简单的运算,就可以得到实际的流量:
引用
# iptables -L -v -n -x|grep '192.168.228.200';sleep 3;iptables -L -v -n -x|grep '192.168.228.200'
2872143 365711591 ACCEPT     all  --  *      *       192.168.228.200      0.0.0.0/0
3555831 3297100630 ACCEPT     all  --  *      *       0.0.0.0/0            192.168.228.200
2872750 365777302 ACCEPT     all  --  *      *       192.168.228.200      0.0.0.0/0
3556591 3297814562 ACCEPT     all  --  *      *       0.0.0.0/0            192.168.228.200
# echo '(3297814562-3297100630)/1024/3'|bc
232
# echo '(365777302-365711591)/1024/3'|bc
21

原理就是这么简单。
※ 注意,FORWARD chain记录的流量中,不经过该网关转发的流量不会记录。也就是说,若你从该服务器上直接下载,流量是记录在INPUT和OUTPUT chain,而不是FORWARD中的。要统计那些数据,方法是相同的。

三、脚本
1、源码
$SEC是间隔的时间,时间太短误差比较大;$ZERO决定是否显示没变化IP。同时,显示被屏蔽的IP地址。

#!/usr/bin/perl -w
# Date:2009-03-12
# Author:HyphenWang
# Version:1.0
use strict;
my $IPTABLES_CMD="iptables -v -n -x -L FORWARD";
my $SEC="3";
my $ZERO="0";
my (%first_input,%first_output);
my (%second_input,%second_output);
my %ban_ip;

sub get_ipflow {
  my ($ip_input,$ip_output)=@_;
  for my $line (`$IPTABLES_CMD`) {
    my @columns = split(/\s+/,$line);
    $ip_input->{$columns[-1]}=$columns[2] if ($columns[3] eq "ACCEPT" and $columns[-1] =~ m/192\.168\.228\.\d+/);
    $ip_output->{$columns[-2]}=$columns[2] if ($columns[3] eq "ACCEPT" and $columns[-2] =~ m/192\.168\.228\.\d+/);
    $ban_ip{$columns[-1]}=1 if ($columns[3] eq "DROP" and $columns[-1] =~ m/192\.168\.228\.\d+/);
    $ban_ip{$columns[-2]}=1 if ($columns[3] eq "DROP" and $columns[-2] =~ m/192\.168\.228\.\d+/);
  }
}
get_ipflow(\%first_input,\%first_output);
sleep $SEC;
get_ipflow(\%second_input,\%second_output);
print "Now is ".localtime()."\n";
print "-"x53,"\n";
print "IP Address\t\tIn Flow Rate\tOut Flow Rate\n";
for (keys %first_input) {
  if ($ZERO != 1) {
    if (defined $second_input{$_} and defined $second_output{$_} and int(($second_input{$_}-$first_input{$_})/1024/$SEC) == 0) {
      next;
    }
  }
  if (defined $second_input{$_} and defined $second_output{$_}) {
  printf ("%s\t\t%.fKB\t\t%.fKB\n",$_,($second_input{$_}-$first_input{$_})/1024/$SEC,($second_output{$_}-$first_output{$_})/1024/$SEC);
  }
}
print "-"x53,"\n";
print "Banned IP Address:\n";
for (keys %ban_ip) {
  print "$_\n";
}

2、结果
◎ ZERO为非1的情况
引用
# perl ipflow.pl
Now is Thu Mar 12 18:35:10 2009
-----------------------------------------------------
IP Address              In Flow Rate    Out Flow Rate
192.168.228.212         277 KByte/s     27 KByte/s
192.168.228.200         40 KByte/s      16 KByte/s

-----------------------------------------------------
Banned IP Address:
192.168.228.50

◎ ZERO为1的情况
引用
# perl ipflow.pl
Now is Thu Mar 12 18:36:21 2009
-----------------------------------------------------
IP Address              In Flow Rate    Out Flow Rate
192.168.228.219         0 KByte/s       0 KByte/s
192.168.228.150         0 KByte/s       0 KByte/s
192.168.228.153         0 KByte/s       0 KByte/s
192.168.228.215         0 KByte/s       0 KByte/s
192.168.228.212         220 KByte/s     27 KByte/s
192.168.228.200         14 KByte/s      9 KByte/s

192.168.228.154         0 KByte/s       0 KByte/s
192.168.228.220         0 KByte/s       0 KByte/s
192.168.228.99          0 KByte/s       0 KByte/s
192.168.228.216         0 KByte/s       0 KByte/s
192.168.228.211         0 KByte/s       0 KByte/s
192.168.228.155         0 KByte/s       0 KByte/s
192.168.228.218         21 KByte/s      1 KByte/s
192.168.228.30          0 KByte/s       0 KByte/s
192.168.228.221         0 KByte/s       0 KByte/s
-----------------------------------------------------
Banned IP Address:

192.168.228.50


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 在Linux环境下,有多种设置IP地址的方式,以下是其中几种: 1. 使用ifconfig命令设置IP地址。该命令可以用来查看和配置络接口及其参数,包括IP地址、子掩码、关等。例如,要将eth0的IP地址设置为192.168.1.100,可以使用以下命令: ``` sudo ifconfig eth0 192.168.1.100 netmask 255.255.255.0 ``` 2. 使用ip命令设置IP地址。ip命令比ifconfig命令更加强大,可以用来配置络接口、由、策略由等。例如,要将eth0的IP地址设置为192.168.1.100,可以使用以下命令: ``` sudo ip addr add 192.168.1.100/24 dev eth0 ``` 3. 修改配置文件/etc/network/interfaces。该文件用来配置络接口的信息,包括IP地址、子掩码、关等。例如,要将eth0的IP地址设置为192.168.1.100,可以编辑该文件并添加以下行: ``` iface eth0 inet static address 192.168.1.100 netmask 255.255.255.0 ``` 以上是设置IP地址的几种方式,选择适合自己的方式进行设置即可。需要注意的是,设置IP地址后需要重启络服务或重启计算机才能生效。 ### 回答2: 在Linux环境下,设置IP地址可以通过多种方式实现。 一种常见的方式是通过命令行工具ifconfig来进行设置。可以使用ifconfig命令查询和配置络接口的信息,包括IP地址、子掩码、关等。例如,使用以下命令设置IP地址为192.168.1.100的eth0接口: ifconfig eth0 192.168.1.100 netmask 255.255.255.0 另一种方式是通过络管理工具Network Manager来进行设置。Network Manager提供了图形化界面来管理络连接和配置。可以通过在系统托盘中找到Network Manager图标,并选择相应的接口进行配置。在Network Manager中,可以设置IP地址、子掩码、关、DNS服务器等。 还有一种设置IP地址的方式是通过编辑络配置文件来实现。在大多数Linux发行版中,络配置文件位于/etc/sysconfig/network-scripts/目录下。可以使用编辑器打开对应的接口的配置文件,如ifcfg-eth0。在文件中,可以手动设置IPADDR、NETMASK和GATEWAY等参数的值。 此外,还可以使用动态主机配置协议(Dynamic Host Configuration Protocol,DHCP)来自动分配IP地址。DHCP服务器可以为计算机自动分配IP地址、子掩码和关等络配置信息。在Linux中,可以使用DHCP客户工具dhclient来请求和获取DHCP服务器分配的络配置信息。 总之,在Linux环境下,我们可以通过ifconfig命令、Network Manager图形工具、编辑络配置文件和使用DHCP来设置IP地址。根据需要选择适合自己的方式进行配置。 ### 回答3: 在Linux环境下,设置IP地址有多种方式,以下是几种常见的方法: 1. 使用ifconfig命令:ifconfig命令可以用于配置络接口的参数,包括IP地址。在终输入以下命令即可配置IP地址: ifconfig [接口名] [IP地址] 2. 使用ip命令:ip命令是ifconfig命令的替代品,也可以用于配置IP地址。例如,以下命令可以配置IP地址: ip addr add [IP地址] dev [接口名] 3. 修改配置文件:可以通过编辑络配置文件来设置IP地址。在大多数Linux发行版中,络配置文件位于/etc/network/interfaces或/etc/sysconfig/network-scripts/目录中。打开该文件,在相应的接口设置中添加或编辑IP地址。 4. DHCP自动获取IP地址:如果你的络使用动态主机配置协议(DHCP),则可以通过在络配置文件中设置接口为DHCP模式,自动获取IP地址。例如,将如下行添加到络配置文件中: dhcp [接口名] 5. 使用Network Manager:Network Manager是一个络配置和管理工具,大多数Linux发行版都默认安装。可以使用图形界面的Network Manager配置IP地址。在桌面环境中,点击络图标,选择“编辑连接”,然后在IPv4或IPv6设置中手动输入IP地址。 无论使用哪种方法,配置IP地址后,需要通过ifup命令使络接口重新启动,以使更改生效。 需要注意的是,更改IP地址可能会导致络连接中断,因此在进行更改前,最好做好相关备份,并根据具体络环境和需求选择合适的方法。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值