Linux系统Perl精简版netstat
来源:优易学  2011-11-24 13:41:34   【优易学:中国教育考试门户网】   资料下载   IT书店
  写作意图:
  Linux系统自带的netstat在很多时候抓信息会发现耗CPU很高,特别是在做一些监控系统的时候,发现如果使用了netstat,监控系统本身会造成系统负载比较高,因此试着用perl写下,time测试比自带的netstat更快更节省资源,青年人网提示欢迎批评,呵呵。
  #!/usr/bin/perl
  # Written by FinalBSD at 2008-11-20.
  # The netstat original written by C
  # is expensive to me, so this born.
  # As long as you retain this notice you
  # can do whatever you want with this stuff.
  # If we meet some day, and you think
  # this stuff is worth it, you can
  # buy me a beer in return.
  use strict;
  use warnings;
  use Getopt::Std;
  my $tcp = "/proc/net/tcp";
  my $tcp6 = "/proc/net/tcp6";
  my $route = "/proc/net/route";
  my @tcpState = (
  "NULL",
  "ESTABLISHED" ,
  "SYN_SENT",
  "SYN_RECV",
  "FIN_WAIT1",
  "FIN_WAIT2",
  "TIME_WAIT",
  "CLOSE",
  "CLOSE_WAIT",
  "LAST_ACK",
  "LISTEN",
  "CLOSING"
  );
  my @routeType = (
  "NULL",
  "U", # UP
  "G", # Gateway
  "UG" # UP & Gateway
  );
  my %opts;
  getopts('nhatsrl', \%opts);
  if($opts{h}) {
  &usage();
  }
  if($opts{r}) {
  &route_info($route);
  exit;
  }
  &tcp_info($tcp);
  &tcp_info($tcp6);
  ######## FUNCTION DEFINITION ######
  #############################
  # Get statistics Information
  ############################
  sub tcp_info($) {
  my $file = shift;
  open(FH, $file) or die("$!");
  my $format = "%-30s %-30s %-10s\n";
  printf($format," Local Address"," Foreign Address","State");
  while(<FH>) {
  next if /local_address/;
  my @data = split;
  my $state = $tcpState[hex($data[3])];
  # Show listening Sockets.
  if($opts{l}){
  printf($format, &hextoint($data[1]), &hextoint($data[2]), $state) if $state =~ /LIST/;
  } else {
  printf($format, &hextoint($data[1]), &hextoint($data[2]), $state);
  }
  }
  close(FH);
  }
  #############################
  # Convert hex to int
  ############################
  sub hextoint($) {
  my $tmp = shift;
  my @data;
  my @ip;
  my $int;
  # if have ':', then it's addr:port,else just port.
  if( $tmp =~ /:/ ) {
  if( $tmp =~ /FFFF/ ) {
  @data = split /:/, $tmp;
  # break it and do convert later.
  @ip = $data[0] =~ /\w{2}/g;
  foreach my $index (12..15){
  $ip[$index] = hex($ip[$index]);
  }
  $int = sprintf("%-5s %d.%d.%d.%d:%d", "tcp6",$ip[15], $ip[14], $ip[13], $ip[12], hex($data[1]));
  } else {
  @data = split /:/, $tmp;
  @ip = $data[0] =~ /\w{2}/g;
  foreach my $index (0..3){
  $ip[$index] = hex($ip[$index]);
  }
  $int = sprintf("%-s %d.%d.%d.%d:%d", " ",$ip[3], $ip[2], $ip[1], $ip[0], hex($data[1]));
  }
  } else {
  @ip = $tmp =~ /\w{2}/g;
  foreach my $index (0..3){
  $ip[$index] = hex($ip[$index]);
  }
  $int = sprintf("%d.%d.%d.%d", hex($ip[3]), hex($ip[2]), hex($ip[1]), hex($ip[0]));
  }
  return $int;
  }
  #############################
  # Show Kernel route table
  ############################
  sub route_info($) {
  my $routefile = shift;
  open(ROUTE, $routefile) or die ("Can't open route file!\n");
  my $header = "Iface Destination Gateway Flags Genmask\n";
  printf("%s", $header);
  my $format = "%-5s %-15s %-15s %-5s %-15s\n";
  while(<ROUTE>) {
  next if /Iface/;
  my @line = split;
  my ($iface, $dest, $gw, $flags, $mask ) = ($line[0], &hextoint($line[1]), &hextoint($line[2]), hex($line[3]), &hextoint($line[7]));
  printf($format, $iface, $dest, $gw, $routeType[$flags], $mask );
  }
  close(ROUTE);
  }
  #############################
  # Show help information
  ############################
  sub usage {
  printf("%s\n\n%-30s\n%-30s\n%-30s\n%-30s\n%-30s\n%-30s\n",
  "netstat written in Perl by FinalBSD.Copyright(c) 2008.",
  "-n Show numeric ip and port address.",
  "-r Display the kernel routing table.",
  "-a Show both listening and non-listening socktes.",
  "-t Show only TCP statistics.",
  "-l Show only listening sockets.",
  "-h Show help.",
  );
  exit;
  }

责任编辑:小草

文章搜索:
 相关文章
热点资讯
热门课程培训