#!/usr/bin/perl

# monEthNet  (c) Copyright 1998 Mark Black 

# NOTE:  If you modify this code, you MUST change the version to
#        something over 100 to prevent it being replaced by future
#        versions of this script. 
$version = 2 ;

# monEthNet [-v|-i]
# This script is called to monitor the Network card utilization
# Outputs status to stdout in the form  status:info
# status can be 0 or 1.  1 = success, 0 = fail
# NOTE:  The script should not have a reason to output a fail
# The info is in the form:    interface0,rx,rx_err,tx,tx_err,coll:interface1,rx,rx_err,tx,tx_err,coll:...
#   -v  - Output the version number
#   -i  - Output a list of the instances of network interfaces

$input = "" ;
foreach $i (0 .. $#ARGV) {
   $input .= "@ARGV[$i] " ;
}
chop($input) ;

# Location of MAT tmp dir
$mattmp = "tmp" ;

# Output the version if requested
if($input eq "-v") {
    print "$version\n" ;
    exit(0) ;
}


# Discover OS type and set variables for OS type
chop($os = `uname -s`) ;

if($os eq "Linux") {
    $netstat = "/bin/netstat" ;
    $discard = 2 ;
    $OS="linux" ;
} elsif($os eq "SunOS") {
    chop($ver = `uname -r`) ;
    ($major, $minor) = split(/\./, $ver) ;
    if($major == 5) {
	$netstat = "/usr/bin/netstat" ;
	$discard = 1 ;
	$OS = "solaris" ;
    } else {
	$netstat = "/usr/ucb/netstat" ;
	$discard = 1 ;
	$OS = "sunos" ;
    }
} elsif(($os eq "IRIX") | ($os eq "IRIX64"))  {
    $discard = 1 ;
    $OS = "irix" ;
    $netstat = "/usr/etc/netstat" ;
} elsif($os eq "HP-UX") {
    $discard = 1 ;
    $OS = "hpux" ;
    $netstat = "/usr/bin/netstat" ;
}


$cargs = "-i" ;

@data = `$netstat $cargs` ;
@deltaout = "" ;

# Parse the output from netstat
# Drop $discard lines
for ( 1 .. $discard ) {
    $line = shift(@data) ;
}

while ($line = shift(@data)) {
    # Parse based on type
    if ($OS eq "linux") {
	($interface, $a, $b, $rx, $rxerr, $rxe1, $rxe2, $tx, $txerr, $txe1, $txe2, $e) = split(/\s+/, $line, 12) ;
	$coll = $rxe1 + $rxe2 + $txe1 + $txe2 ;
    } elsif($OS eq "solaris" | $OS eq "irix" | $OS eq "sunos") {
	($interface, $a, $b, $c, $rx, $rxerr, $tx, $txerr, $coll, $e) = split(/\s+/, $line, 10) ;
    } elsif($OS eq "hpux" ) {
	($interface, $a, $b, $c, $rx, $rxerr, $tx, $txerr, $coll, $e) = split(/\s+/, $line, 10) ;
    } 
    
    # Remove the ni0, ni1, interfaces from teh HPUX netstat
    if($OS eq "hpux" ) {
	if( $interface =~ m/^ni.+/) {
	    # Print nothing
	} else {
	    # Make a new data line for the delta calculation
	    $dout = "$interface:$rx:$rxerr:$tx:$txerr:$coll\n" ;
	    push(@deltaout, $dout) ;
	}
    } else {
	# Make a new data line for the delta calculation
	$dout = "$interface:$rx:$rxerr:$tx:$txerr:$coll\n" ;
	push(@deltaout, $dout) ;
    }
}


# Was the instance of network devices requested?
if($input eq "-i") {
    $cnt = 0 ;
    $outstr = "" ;
    foreach $d (1..$#deltaout) {
	($intf, $junk) = split(/\:/, @deltaout[$d], 2) ;
	$outstr .= "$intf:" ;
	$cnt++ ;
    }
    chop($outstr) ;
    print "$cnt:$outstr\n" ;
    exit(0) ;
}


# Look for a delta file
$ext = open(DLTFILE, "$mattmp/monEthNet.tmp0123") ;
if ($ext) {
    # File exists:  Read it
    @din = <DLTFILE> ;
    close DLTFILE ;
    print "1" ;
    foreach $d (1..$#deltaout) {
	# Compute the delta's for the packets
	($intf, $rx, $rxerr, $tx, $txerr, $coll) = split(/\:/, @deltaout[$d], 6) ;
	($intfo, $rxo, $rxerro, $txo, $txerro, $collo) = split(/\:/, @din[$d-1], 6) ;
	if ( $intf ne $intfo ) {
	    # Error names don't match !
	    print ":$intf:0:0:0:0:0" ;
	} else {
	    # Names match, so output delta
	    $drx = $rx - $rxo ;
	    $drxerr = $rxerr - $rxerro ;
	    $dtx = $tx - $txo ;
	    $dtxerr = $txerr - $txoerr ;
	    chop($c = $coll) ;
	    chop($co = $collo) ;
	    $dcoll = $c - $co ;
	    # Values < 0 indicate a reboot
	    if ( $drx < 0 | $dtx < 0 ) {
		print ":$intf:0:0:0:0:0" ;
	    } else { 
		print ":$intf:$drx:$drxerr:$dtx:$dtxerr:$dcoll" ;
	    }
	}
    }
    print "\n" ;

    # Output the current stats for later use
    $ext = open(DLTFILE, "> $mattmp/monEthNet.tmp0123") ;
    print DLTFILE @deltaout ;
    close DLTFILE ;
    exit 0 ;

} else {
    # File does not exist 

    # Output data to the Delta file
    close DLTFILE ;
    $ext = open(DLTFILE, "> $mattmp/monEthNet.tmp0123") ;
    if (!$ext) { 
	print "0:lo:0:0:0:0:0\n" ; 
	exit 0 ; 
    } 
    print DLTFILE @deltaout ;
    close DLTFILE ;

    print "1" ;
    foreach $d (1..$#deltaout) {
	($intf, $a) = split(/\:/, @deltaout[$d], 2) ;
	print ":$intf:0:0:0:0:0" ;
    }
    print "\n" ;
    close DLTFILE ;
    
    exit 0 ;
}






