/[perl]/istatd.pl
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Contents of /istatd.pl

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1.2 - (show annotations)
Tue Jun 24 21:18:21 2003 UTC (20 years, 9 months ago) by dpavlin
Branch: MAIN
CVS Tags: HEAD
Changes since 1.1: +118 -103 lines
File MIME type: text/plain
support for more than one interface

1 #!/usr/bin/perl -w
2
3 # This program is free software; you can redistribute it and/or modify
4 # it under the terms of the GNU General Public License as published by
5 # the Free Software Foundation; either version 2 of the License, or
6 # (at your option) any later version.
7 #
8 # This program is distributed in the hope that it will be useful,
9 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 # GNU General Public License for more details.
12 #
13 # You should have received a copy of the GNU General Public License
14 # along with this program; if not, write to the Free Software
15 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16 #
17
18 use POSIX;
19 use RRDs;
20 use strict;
21
22 #
23 # Basic setup
24 #
25
26 my @ifaces = qw(wlan0 eth0 eth1); # wireless and other interface
27 my $step = 10; # sec
28 my $next1_factor = 60; # $step * $next1_factor = 10*60 = 600 sec = 10 min
29 my $next2_factor = 360; # $step * $next2_factor = 10*360 = 3600 sec = 1 hour
30 my $update_graph_period = 10; # How often will be graph updated (1..1000)
31
32 #
33 # Setup files locations
34 #
35
36 my $wifi_proc_file='/proc/net/wireless';
37 my $dev_proc_file='/proc/net/dev';
38 my ($pid_file,$base_dir);
39 if ($0 =~ m#^(.*?)/(.+)\.pl$#i) {
40 $base_dir = $1;
41 $pid_file = "$base_dir/$2.pid";
42 } else {
43 die "can't decode base dir and script name from '$0'";
44 }
45
46 #
47 # End setup
48 #
49 ############################################################
50
51 my $start=time;
52 my $syncrorun;
53 my $switcher=$ARGV[0];
54 if (!($switcher)) { $switcher='undef'; }
55
56 if ($switcher eq 'start') {
57 &start();
58 } elsif ($switcher eq 'stop') {
59 &stop();
60 } elsif ($switcher eq 'graph') {
61 foreach (@ifaces) {
62 &update_graph($_);
63 }
64 } elsif ($switcher eq 'install') {
65 foreach (@ifaces) {
66 &install($_);
67 }
68 } else {
69 print qq(Usage: ./istatd.pl option
70 option: start - Starting daemon
71 stop - Stopping daemon
72 graph - Get the latest graph
73 install - Init database
74 );
75 }
76
77 ###############################################################
78 sub install {
79 my $iface = shift || die "need interface name!";
80 my $rrd = "$base_dir/$iface.rrd";
81 my $sec_in_the_day=86400;
82 my $sec_in_the_week=$sec_in_the_day*7;
83 my $sec_in_the_month=$sec_in_the_day*31;
84 my $minvalue=0;
85 my $maxvalue=255;
86 my $xfiles_factor=0.5;
87 my $max_interval=$step/$xfiles_factor;
88 my $number_steps_day=floor($sec_in_the_day/$step);
89 my $number_steps_week=floor($sec_in_the_week/($step*$next1_factor));
90 my $number_steps_month=floor($sec_in_the_month/($step*$next2_factor));
91 RRDs::create ($rrd, "--start",$start-1, "--step",$step,
92 "DS:link:GAUGE:$max_interval:$minvalue:$maxvalue",
93 "DS:level:GAUGE:$max_interval:$minvalue:$maxvalue",
94 "DS:noise:GAUGE:$max_interval:$minvalue:$maxvalue",
95 "DS:in:COUNTER:$max_interval:0:U",
96 "DS:out:COUNTER:$max_interval:0:U",
97 "RRA:AVERAGE:$xfiles_factor:1:$number_steps_day",
98 "RRA:AVERAGE:$xfiles_factor:$next1_factor:$number_steps_week",
99 "RRA:AVERAGE:$xfiles_factor:$next2_factor:$number_steps_month");
100 my $ERROR = RRDs::error;
101 die "$0: unable to create `$rrd': $ERROR\n" if $ERROR;
102 print "$iface done.\n";
103 }
104
105 ###############################################################
106 sub start {
107 my $pid=fork;
108 exit if $pid;
109 die "Could't fork: $!" unless defined($pid);
110 POSIX::setsid() or die "Can't start a new session: $!";
111 $SIG{INT}=$SIG{TERM}=$SIG{HUP}=\&syncro_handler;
112 $syncrorun=1;
113 my $pid_id=$$;
114 open(FILE, ">>$pid_file") || die "Cant write to $pid_file file: $!";
115 print FILE $pid_id;
116 close(FILE);
117 my $counter=0;
118 while ($syncrorun) {
119 $counter++;
120 if (!( -e $pid_file)) { $syncrorun=0; }
121 foreach (@ifaces) {
122 &get_data($_);
123 }
124 if ($counter == $update_graph_period) {
125 foreach (@ifaces) {
126 &update_graph($_);
127 }
128 $counter=0;
129 }
130 sleep($step);
131 }
132 }
133
134 ##############################################################
135 sub stop {
136 my $pid=`cat $pid_file`;
137 `kill $pid`;
138 }
139
140 ##############################################################
141 sub update_graph {
142 my $iface = shift || die "need interface name!";
143 my $rrd = "$base_dir/$iface.rrd";
144
145 RRDs::graph "$iface-signal.png",
146 "--title", " $iface signal statistics",
147 "--start", "now-12h",
148 "--end", "now",
149 "--lower-limit=0",
150 "--interlace",
151 "--imgformat","PNG",
152 "--width=450",
153 "DEF:link=$rrd:link:AVERAGE",
154 # "DEF:level=$rrd:level:AVERAGE",
155 # "DEF:noise=$rrd:noise:AVERAGE",
156 "AREA:link#00b6e4:link",
157 # "LINE1:level#0022e9:level",
158 # "LINE1:noise#cc0000:noise"
159 ;
160 print "ERROR ".RRDs::error."\n" if (RRDs::error);
161
162 RRDs::graph "$iface-transfer.png",
163 "--title", " $iface transfer statistics",
164 "--start", "now-12h",
165 "--end", "now",
166 "--lower-limit=0",
167 "--interlace",
168 "--imgformat","PNG",
169 "--width=450",
170 "DEF:in=$rrd:in:AVERAGE",
171 "DEF:out=$rrd:out:AVERAGE",
172 "AREA:in#00b6e4:in",
173 "LINE1:out#0022e9:out",
174 ;
175 print "ERROR ".RRDs::error."\n" if (RRDs::error);
176 }
177
178 ###############################################################
179 sub get_data {
180 my $iface = shift || die "need interface name!";
181 my $rrd = "$base_dir/$iface.rrd";
182
183 my ($link,$level,$noise,$in,$out) = ("U","U","U","U","U");
184
185 open(FILE, "$wifi_proc_file") || die "Cant open $wifi_proc_file file: $!";
186 while (my $line=<FILE>) {
187 ($link,$level,$noise) = ($1,$2,$3) if ($line=~/\s*?$iface\:\s+?\d+?\s+?(\d+)\.*?\d*?\s+?(\d+)\.*?\d*?\s+?(\d+)\.*?\d*?.*/);
188 }
189 close(FILE);
190
191 open(FILE, "$dev_proc_file") || die "Cant open $dev_proc_file file: $!";
192 while (my $line=<FILE>) {
193 if ($line=~/\s*?$iface\:\s*?(\d+.*)$/) {
194 my @v = split(/\s+/,$1,16);
195 ($in,$out) = ($v[0],$v[8]);
196 }
197 }
198 close(FILE);
199 RRDs::update ("$rrd", "--template", "link:level:noise:in:out", "N:$link:$level:$noise:$in:$out");
200 print "ERROR ".RRDs::error."\n" if (RRDs::error);
201 }
202
203 ###############################################################
204 sub syncro_handler {
205 unlink($pid_file) || die "Cant unlink $pid_file file: $!";
206 $syncrorun=0;
207 }

  ViewVC Help
Powered by ViewVC 1.1.26