Browse Source

Add ./tarball_archive/symon-2.55.tar.gz

Wictor Lund 4 years ago
parent
commit
7e804206ab
65 changed files with 2120 additions and 1144 deletions
  1. 23 1
      symon/CHANGELOG
  2. 23 1
      symon/INSTALL
  3. 3 3
      symon/Makefile
  4. 12 3
      symon/Makefile.inc
  5. 14 0
      symon/client/Makefile
  6. 288 0
      symon/client/SymuxClient.pm
  7. 16 0
      symon/client/getsymonitem.pl
  8. 218 182
      symon/lib/data.c
  9. 86 62
      symon/lib/data.h
  10. 32 29
      symon/lib/error.c
  11. 6 6
      symon/lib/error.h
  12. 60 54
      symon/lib/lex.c
  13. 27 26
      symon/lib/lex.h
  14. 169 61
      symon/lib/net.c
  15. 15 7
      symon/lib/net.h
  16. 7 7
      symon/lib/xmalloc.c
  17. 6 6
      symon/lib/xmalloc.h
  18. 4 2
      symon/ports/symon/Makefile
  19. 25 0
      symon/ports/symon/pkg/DEINSTALL
  20. 2 2
      symon/ports/symon/pkg/DEINSTALL-mon
  21. 67 0
      symon/ports/symon/pkg/INSTALL
  22. 5 1
      symon/ports/symon/pkg/PLIST
  23. 4 1
      symon/ports/symon/pkg/PLIST-mux
  24. 1 0
      symon/ports/symon/pkg/PLIST-web
  25. 3 3
      symon/symon/Makefile
  26. 2 2
      symon/symon/c_config.sh
  27. 51 55
      symon/symon/readconf.c
  28. 2 14
      symon/symon/readconf.h
  29. 15 15
      symon/symon/sm_cpu.c
  30. 80 0
      symon/symon/sm_debug.c
  31. 18 20
      symon/symon/sm_if.c
  32. 14 14
      symon/symon/sm_io.c
  33. 16 17
      symon/symon/sm_mem.c
  34. 10 10
      symon/symon/sm_pf.c
  35. 8 7
      symon/symon/symon.8
  36. 48 40
      symon/symon/symon.c
  37. 19 16
      symon/symon/symon.h
  38. 38 41
      symon/symon/symonnet.c
  39. 2 2
      symon/symon/symonnet.h
  40. 1 0
      symon/symon2web/Makefile
  41. 1 0
      symon/symon2web/class_cpu.inc
  42. 1 2
      symon/symon2web/class_graph.inc
  43. 1 0
      symon/symon2web/class_if.inc
  44. 1 0
      symon/symon2web/class_io.inc
  45. 1 0
      symon/symon2web/class_mem.inc
  46. 1 0
      symon/symon2web/class_pf.inc
  47. 1 0
      symon/symon2web/graph_cpu.php
  48. 1 0
      symon/symon2web/graph_if.php
  49. 1 0
      symon/symon2web/graph_io.php
  50. 1 0
      symon/symon2web/graph_mem.php
  51. 1 0
      symon/symon2web/graph_pf.php
  52. 2 0
      symon/symon2web/index.php
  53. 78 0
      symon/symon2web/test_config.php
  54. 0 4
      symon/symux/.gdbinit
  55. 21 4
      symon/symux/c_smrrds.sh
  56. 138 109
      symon/symux/readconf.c
  57. 3 5
      symon/symux/readconf.h
  58. 142 96
      symon/symux/share.c
  59. 15 14
      symon/symux/share.h
  60. 20 15
      symon/symux/symux.8
  61. 80 71
      symon/symux/symux.c
  62. 2 2
      symon/symux/symux.conf
  63. 3 3
      symon/symux/symux.h
  64. 158 98
      symon/symux/symuxnet.c
  65. 7 11
      symon/symux/symuxnet.h

+ 23 - 1
symon/CHANGELOG

@@ -1,3 +1,25 @@
+29/11/2002 - 2.55
+
+   Markus Friedl reported that unresolvable ip addresses cannot be used in the
+   configuration file - fixed.
+
+   Overhauled the networking code. Everything is now ip6 aware. This does mean
+   that the ':' is no longer a keyword in the lexer; i.e. '<host>:<port>'
+   statements should now be written as '<host> <port>' or '<host> port <port>'.
+
+   Added the debug module. This can be used to retrieve debug0 ... debug19
+   variables from the kernel.
+
+08/11/2002 - 2.54
+
+   Added a perl module that allows ppl to connect to symux and do something
+   with the measurements as they come in. (I plan to drive an LCD using this,
+   but it could also be used to get, say, daily bandwidth usage)
+ 
+   Clients of symux would not sleep after they had read and relayed data symux
+   gave to them. This could lead to one child eating up multiple 'semaphore
+   slots' and starvation in other clients - fixed.
+
 25/10/2002 - 2.53
 25/10/2002 - 2.53
 
 
    Henning Brauer suggested a datadir statement for symux configuration -
    Henning Brauer suggested a datadir statement for symux configuration -
@@ -196,4 +218,4 @@
 29/09/2001 - Lexer had trouble dealing with ip-addresses. Cleaned up the number	
 29/09/2001 - Lexer had trouble dealing with ip-addresses. Cleaned up the number	
              parsing code and removed a second comment reader.
              parsing code and removed a second comment reader.
 
 
-$Id: CHANGELOG,v 1.8 2002/10/18 12:29:09 dijkstra Exp $
+$Id: CHANGELOG,v 1.10 2002/11/29 10:50:28 dijkstra Exp $

+ 23 - 1
symon/INSTALL

@@ -77,6 +77,11 @@ Less quick, but more verbose
   the symon2web/datasources.inc to reflect your filelocations. datasources.inc
   the symon2web/datasources.inc to reflect your filelocations. datasources.inc
   also contains some settings on how the data is displayed.
   also contains some settings on how the data is displayed.
 
 
+  symon2web runs 'rrdtool' to generate graphs as requests for pictures come
+  in. As of OpenBSD 3.2 apache is chrooted at /var/www. Make sure a statically
+  linked rrdtool is available, or break the chroot. You were not planning of
+  running this software on a machine tied to the internet anyway.
+
      + $symon2web["view"] = show all graphs for all machines ('all') or show
      + $symon2web["view"] = show all graphs for all machines ('all') or show
        only graphs for a single selected machine ('one').
        only graphs for a single selected machine ('one').
 
 
@@ -89,6 +94,23 @@ Less quick, but more verbose
           'big'    =  600 x 450, 
           'big'    =  600 x 450, 
           'huge'   = 1024 x 640.
           'huge'   = 1024 x 640.
 
 
+     + test your setup with test_config.php - this will try to run rrdtool and
+       see if your rrd files are accessable by symon2web.
+
+Getting measurements without the web
+====================================
+
+The client directory contains a perl module 'SymuxClient.pm' that can be used
+to read measurements as they come in at the symux host. A sample Perl program
+called 'getsymonitem.pl' shows how to use the module. 
+
+Example:
+
+hoard$ getsymonitem.pl 127.0.0.1 2100 127.0.0.1 "cpu(0)" "idle"
+93.40
+
+Historical data can be gathered using rrdfetch(1) from symux's rrd files.
+
 Portability
 Portability
 ===========
 ===========
 
 
@@ -98,5 +120,5 @@ symon2web run on POSIX compliant unixes, but the monitoring application itself
 
 
 Willem Dijkstra <wpd@xs4all.nl>
 Willem Dijkstra <wpd@xs4all.nl>
 
 
-$Id: INSTALL,v 1.7 2002/10/18 12:29:09 dijkstra Exp $
+$Id: INSTALL,v 1.9 2002/11/29 10:50:28 dijkstra Exp $
 
 

+ 3 - 3
symon/Makefile

@@ -1,6 +1,6 @@
-# $Id: Makefile,v 1.9 2002/09/14 15:58:45 dijkstra Exp $
+# $Id: Makefile,v 1.10 2002/11/08 15:40:11 dijkstra Exp $
 
 
-SUBDIR=	lib symon symux symon2web
+SUBDIR=	lib symon symux symon2web client
 
 
 .if make(clean)
 .if make(clean)
 SUBDIR+= ports/symon
 SUBDIR+= ports/symon
@@ -20,7 +20,7 @@ dist: clean
 	${MAKE} clean; \
 	${MAKE} clean; \
 	cd ../../..; \
 	cd ../../..; \
 	echo Exporting symon-${V}.tar.gz; \
 	echo Exporting symon-${V}.tar.gz; \
-	find $${workdir} -type f -print | egrep -v 'CVS|doc|clients|README|regress|#'| \
+	find $${workdir} -type f -print | egrep -v 'CVS|doc|README|regress|#'| \
 		tar -czvf /tmp/symon-${V}.tar.gz -I -; \
 		tar -czvf /tmp/symon-${V}.tar.gz -I -; \
 	cp /tmp/symon-${V}.tar.gz /usr/ports/distfiles/; \
 	cp /tmp/symon-${V}.tar.gz /usr/ports/distfiles/; \
 	cd $${workdir}/ports/symon; \
 	cd $${workdir}/ports/symon; \

+ 12 - 3
symon/Makefile.inc

@@ -1,6 +1,6 @@
-# $Id: Makefile.inc,v 1.10 2002/10/18 12:29:09 dijkstra Exp $
+# $Id: Makefile.inc,v 1.12 2002/11/29 10:50:28 dijkstra Exp $
 
 
-V=2.53
+V=2.55
 
 
 AR=	ar
 AR=	ar
 CC=	cc
 CC=	cc
@@ -14,11 +14,13 @@ LORDER=	lorder
 NROFF=	nroff
 NROFF=	nroff
 RANLIB= ranlib
 RANLIB= ranlib
 STRIP=  strip
 STRIP=  strip
+POD2MAN= pod2man
 
 
 BINDIR= libexec
 BINDIR= libexec
 MANDIR=	man
 MANDIR=	man
 SHRDIR= share/symon
 SHRDIR= share/symon
 WEBDIR= ${SHRDIR}/web
 WEBDIR= ${SHRDIR}/web
+CLIENTDIR= ${SHRDIR}/client
 
 
 .ifndef PREFIX
 .ifndef PREFIX
 PREFIX=/usr/local
 PREFIX=/usr/local
@@ -28,10 +30,17 @@ PREFIX=/usr/local
 SYSCONFDIR=/etc
 SYSCONFDIR=/etc
 .endif
 .endif
 
 
-.SUFFIXES: .c .o .8 .cat8
+.SUFFIXES: .c .o .8 .cat8 .pm .cat3p
 
 
 .c.o:
 .c.o:
 	${CC} ${CFLAGS} -c $<
 	${CC} ${CFLAGS} -c $<
 
 
 .8.cat8:
 .8.cat8:
 	${NROFF} -mandoc $< > $@ || (rm -f $@; false)
 	${NROFF} -mandoc $< > $@ || (rm -f $@; false)
+		
+.pm.cat3p:
+	${POD2MAN} $< > $@.tmp || (rm -f $@; false)
+	${NROFF} -mandoc $@.tmp > $@ || (rm -f $@; false)
+	rm -f $@.tmp
+
+

+ 14 - 0
symon/client/Makefile

@@ -0,0 +1,14 @@
+# $Id: Makefile,v 1.1 2002/11/08 15:40:25 dijkstra Exp $
+.include "../Makefile.inc"
+
+all: SymuxClient.cat3p
+
+clean:
+	rm -f SymuxClient.cat3p
+
+install: SymuxClient.pm SymuxClient.cat3p getsymonitem.pl
+	${INSTALL} -d -m 555 -g www -o www ${PREFIX}/${CLIENTDIR}
+	${INSTALL} -c -m 555 -g bin   -o root getsymonitem.pl      ${PREFIX}/${CLIENTDIR}
+	${INSTALL} -c -m 444 -g wheel -o root SymuxClient.pm       ${PREFIX}/${CLIENTDIR}
+	${INSTALL} -c -m 444 -g wheel -o root SymuxClient.cat3p    ${PREFIX}/${CLIENTDIR}/SymuxClient.0
+

+ 288 - 0
symon/client/SymuxClient.pm

@@ -0,0 +1,288 @@
+# $Id: SymuxClient.pm,v 1.2 2002/11/29 10:47:35 dijkstra Exp $
+#
+# Copyright (c) 2001-2002 Willem Dijkstra
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+#
+#    - Redistributions of source code must retain the above copyright
+#      notice, this list of conditions and the following disclaimer.
+#    - Redistributions in binary form must reproduce the above
+#      copyright notice, this list of conditions and the following
+#      disclaimer in the documentation and/or other materials provided
+#      with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+# COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+
+package SymuxClient;
+
+use Carp;
+use IO::Socket;
+
+my $streamitem = 
+    {cpu   => {user => 1, nice => 2, system => 3, interrupt => 4, idle => 5},
+     mem   => {real_active => 1, real_total => 2, free => 3, swap_used => 4, 
+	       swap_total =>5},
+     if    => {packets_in => 1, packets_out => 2, bytes_in => 3, bytes_out => 4, 
+	       multicasts_in => 5, multicasts_out => 6, errors_in => 7, 
+	       errors_out => 8, collisions => 9, drops => 10},
+     io    => {total_transfers => 1, total_seeks => 2, total_bytes => 3},
+     pf    => {bytes_v4_in => 1, bytes_v4_out => 2, bytes_v6_in => 3,
+	       bytes_v6_out => 4, packets_v4_in_pass => 5, 
+	       packets_v4_in_drop => 6, packets_v4_out_pass => 7,
+	       packets_v4_out_drop => 8, packets_v6_in_pass => 9, 
+	       packets_v6_in_drop => 10, packets_v6_out_pass => 11,
+	       packets_v6_out_drop => 12, states_entries => 13, 
+	       states_searches => 14, states_inserts => 15, 
+	       states_removals => 16, counters_match => 17, 
+	       counters_badoffset => 18, counters_fragment => 19,
+	       counters_short => 20, counters_normalize => 21, 
+	       counters_memory => 22},
+     debug => {debug0 => 1, debug1 => 2, debug3 => 3, debug4 => 4, debug5 = 5,
+	       debug6 => 6, debug7 => 7, debug8 => 8, debug9 => 9, 
+	       debug10 => 10, debug11 => 11, debug12 => 12, debug13 => 13,
+	       debug14 => 14, debug15 => 15, debug16 => 16, debug17 => 17,
+	       debug18 => 18, debug19 => 19}};
+
+sub new {
+    my ($class, %arg) = @_;
+    my $self;
+    
+    (defined $arg{host} && defined $arg{port}) or 
+        croak "error: need a host and a port to connect to.";
+
+    ($self->{host}, $self->{port}) = ($arg{host}, $arg{port});
+
+    $self->{retry} = (defined $arg{retry}? $arg{retry} : 10);
+
+    bless($self, $class);
+
+    $self->connect();
+
+    return $self;
+}
+
+sub DESTROY {
+    my $self = shift;
+
+    if (defined $self->{sock}) {
+        close($self->{sock});
+    }
+}
+    
+sub connect {
+    my $self = shift;
+
+    if (defined $self->{sock} && $self->{sock}->connected() ne '') {
+        return;
+    } else { 
+        close($self->{sock});
+    }
+    
+    $self->{sock} = new 
+      IO::Socket::INET(PeerAddr => $self->{host},
+                       PeerPort => $self->{port},
+                       Proto => "tcp",
+                       Type => SOCK_STREAM)
+          or croak "error: could not connect to $self->{host}:$self->{port}";
+}
+
+sub getdata {
+    my $self = shift;
+    my $sock;
+    my $data;
+    my $tries;
+
+    $tries = 0;
+
+    while (1) {
+        $self->connect();
+        $sock = $self->{sock};
+        $data = <$sock>;
+        if ((index($data, "\012") != -1) && (index($data, ';') != -1)) {
+            $self->{rawdata} = $data;
+            return $data;
+        } else {
+            croak "error: tried to get data $tries times and failed"  
+                if (++$tries == $self->{retry});
+        }
+    }
+}
+
+sub parse {
+    my $self = shift;
+    my ($stream, @streams, $name, $arg, @data, $number);
+
+    $self->getdata() if ! defined $self->{rawdata};
+
+    $number = 0;
+    undef $self->{data};
+    undef $self->{datasource};
+    chop $self->{rawdata}; # remove ';\n'
+    chop $self->{rawdata};
+
+    @streams = split(/;/, $self->{rawdata});
+    croak "error: expected a symux dataline with ';' delimited streams" 
+        if ($#streams < 2);
+    
+    $self->{datasource} = shift @streams;
+    
+    foreach $stream (@streams) {
+        ($name, $arg, @data) = split(':', $stream);
+        
+        croak "error: expected a symux stream with ':' delimited values"
+            if ($#data < 2);
+
+        $name .= '('.$arg.')' if ($arg ne '');
+
+        @{$self->{data}{$name}} = @data;
+        $number++;
+    }
+
+    $self->{rawdata} = '';
+    return $number;
+}
+
+sub getcacheditem {
+    my ($self, $host, $streamname, $item) = @_;
+    my ($streamtype, @addr, $element);
+
+    return undef if not defined $self->{datasource};
+    return undef if (($host ne $self->{datasource})  && 
+		     ($host ne "*"));
+
+    croak "error: source $host does not contain stream $streamname" 
+        if not defined $self->{data}{$streamname};
+
+    ($streamtype = $streamname) =~ s/^([a-z]+).*/\1/;
+
+    if ($item eq 'timestamp') {
+        $element = 0;
+    } elsif (not defined $$streamitem{$streamtype}{$item}) {
+        croak "error: unknown stream item '$item' - check symux(8) for names";
+    } else {
+        $element = $$streamitem{$streamtype}{$item};
+    }
+        
+    return $self->{data}{$streamname}[$element];
+}
+
+sub getitem {
+    my ($self, $host, $streamname, $item) = @_;
+    my $data;
+    my %hosts = ();
+    
+    undef $data;
+    while (! defined $data) {
+        $self->getdata();
+        $self->parse();
+        $hosts{$self->{datasource}} += 1;
+        if ($hosts{$self->{datasource}} > $self->{retry}) {
+            croak "error: seen a lot of data ($tries strings), but none that matches $host";
+        }
+        $data = $self->getcacheditem($host, $streamname, $item);
+        return $data if defined $data;
+        $tries++;
+    }
+}
+
+sub source {
+    my $self = shift;
+
+    return $self->{datasource};
+}
+1;
+
+__END__
+
+=head1 NAME
+
+SymuxClient - Object client interface for symux
+
+=head1 SYNOPSIS
+
+use SymuxClient;
+
+=head1 DESCRIPTION
+
+C<SymuxClient> provides an object client interface for listening to, and
+parsing of, symux data.
+
+=head1 CONSTRUCTOR
+
+=over 4
+
+=item new ( ARGS )
+
+Creates a new C<SymuxClient> object that holds both the connection to a symux
+and data it receives from that connection. Arguments are:
+
+    host           dotted quad ipv4 hostaddress
+    port           tcp port that symux is on
+    retry*         maximum number of retries; used to limit number 
+                   of connection attempts and number of successive 
+                   read attempts
+
+Arguments marked with * are optional.
+
+Example:
+    $sc = new SymuxClient(host => 127.0.0.1,
+                          port => 2100);
+
+=back 
+
+=head2 METHODS
+
+=item getitem (host, stream, item)
+
+Refresh the measured data and get an item from a stream for a particular
+host. Note that successive calls for this function deal with successive
+measurements of B<symon>. Set C<host> to '*' if data about any host is of
+interest. Any errors are sent out on STDOUT prepended with 'error: '.
+
+=item getcacheditem (host, stream, item)
+
+Get an item from a stream for a particular host. Returns C<undef> if no data is
+cached, or if the data cached does not match the B<host>. Can be called
+multiple times to obtain items from the same measurement. Set C<host> to '*' if
+data about any host is of interest. Any errors are sent out on STDOUT prepended
+with 'error: '.
+
+=item getsource ()
+
+Get the symon source host of the currently cached information. Usefull to see
+what host's data getcacheditem is working on.
+
+Example: 
+    $sc = new SymuxClient(host => 127.0.0.1,
+                          port => 2100);
+
+    print $sc->getitem("127.0.0.1", "if(de0)", 
+                       "packets_out");
+
+    # get more data from that measurement
+    print $sc->getcacheditem("127.0.0.1","if(de0)", 
+                             "packets_in"); 
+
+    # start a new measurement
+    print $sc->getitem("*", "if(de0)", 
+                       "packets_out");
+    # which hosts packets_out was that?
+    print $sc->getsource();
+
+=cut
+

+ 16 - 0
symon/client/getsymonitem.pl

@@ -0,0 +1,16 @@
+#!/usr/bin/perl
+#
+# $Id: getsymonitem.pl,v 1.1 2002/11/08 15:40:25 dijkstra Exp $
+# 
+# Example program of how to use SymuxClient
+
+use SymuxClient;
+
+die "Usage: $0 <symux host> <symux port> <measured host> <stream> <item>
+Example: $0 127.0.0.1 2100 127.0.0.1 'cpu(0)' user\n" if ($#ARGV < 4);
+
+my $sc = new SymuxClient( host => $ARGV[0],
+			  port => $ARGV[1]);
+
+print $sc->getitem( $ARGV[2], $ARGV[3], $ARGV[4] );
+			  

+ 218 - 182
symon/lib/data.c

@@ -1,4 +1,4 @@
-/* $Id: data.c,v 1.16 2002/09/14 15:56:18 dijkstra Exp $ */
+/* $Id: data.c,v 1.17 2002/11/29 10:44:21 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -6,7 +6,7 @@
  *
  *
  * The crc routine is from Rob Warnock <rpw3@sgi.com>, from the
  * The crc routine is from Rob Warnock <rpw3@sgi.com>, from the
  * comp.compression FAQ.
  * comp.compression FAQ.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * modification, are permitted provided that the following conditions
  * are met:
  * are met:
@@ -32,8 +32,8 @@
  * POSSIBILITY OF SUCH DAMAGE.
  * POSSIBILITY OF SUCH DAMAGE.
  * */
  * */
 
 
-/* Terminology: 
- * 
+/* Terminology:
+ *
  * A host carrying a 'symon' is considered a 'source' of information. A single
  * A host carrying a 'symon' is considered a 'source' of information. A single
  * data 'stream' of information has a particular type: <cpu|mem|if|io>. A
  * data 'stream' of information has a particular type: <cpu|mem|if|io>. A
  * source can provide multiple 'streams' simultaniously. A source spools
  * source can provide multiple 'streams' simultaniously. A source spools
@@ -51,22 +51,23 @@
 #include "data.h"
 #include "data.h"
 #include "error.h"
 #include "error.h"
 #include "lex.h"
 #include "lex.h"
+#include "net.h"
 #include "xmalloc.h"
 #include "xmalloc.h"
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
-int            bytelenvar(char);
-int            checklen(int, int, int);
+int bytelenvar(char);
+int checklen(int, int, int);
 struct stream *create_stream(int, char *);
 struct stream *create_stream(int, char *);
-char          *formatstrvar(char);
-char          *rrdstrvar(char);
-int            strlenvar(char);
+char *formatstrvar(char);
+char *rrdstrvar(char);
+int strlenvar(char);
 __END_DECLS
 __END_DECLS
 
 
 /* Stream formats
 /* Stream formats
- * 
+ *
  * Format specifications are strings of characters:
  * Format specifications are strings of characters:
  *
  *
- * L = u_int64 
+ * L = u_int64
  * l = u_int32
  * l = u_int32
  * s = u_int16
  * s = u_int16
  * c = 3.2f <= u_int14 <= u_int16  (used in percentages)
  * c = 3.2f <= u_int14 <= u_int16  (used in percentages)
@@ -76,57 +77,58 @@ struct {
     char type;
     char type;
     char *rrdformat;
     char *rrdformat;
     char *strformat;
     char *strformat;
-    int  strlen;
-    int  bytelen;
+    int strlen;
+    int bytelen;
     u_int64_t max;
     u_int64_t max;
-} streamvar[] = {
-    {'L', ":%llu",  " %20llu",   22, sizeof(u_int64_t), (u_int64_t) 0xffffffffffffffff},
-    {'l', ":%lu",    " %10lu",   12, sizeof(u_int32_t), (u_int64_t) 0xffffffff},
-    {'s', ":%u",       " %5u",    7, sizeof(u_int16_t), (u_int64_t) 0xffff},
-    {'c', ":%3.2f",  " %3.2f",    8, sizeof(u_int16_t), (u_int64_t) 100},
-    {'b', ":%3u",      " %3u",    5, sizeof(u_int8_t),  (u_int64_t) 255},
-    {'\0', NULL,         NULL,    0,                 0,             0}
+}      streamvar[] = {
+    { 'L', ":%llu", " %20llu", 22, sizeof(u_int64_t), (u_int64_t) 0xffffffffffffffff },
+    { 'l', ":%lu", " %10lu", 12, sizeof(u_int32_t), (u_int64_t) 0xffffffff },
+    { 's', ":%u", " %5u", 7, sizeof(u_int16_t), (u_int64_t) 0xffff },
+    { 'c', ":%3.2f", " %3.2f", 8, sizeof(u_int16_t), (u_int64_t) 100 },
+    { 'b', ":%3u", " %3u", 5, sizeof(u_int8_t), (u_int64_t) 255 },
+    { '\0', NULL, NULL, 0, 0, 0 }
 };
 };
 /* streams of <type> have the packedstream <form> */
 /* streams of <type> have the packedstream <form> */
 struct {
 struct {
     int type;
     int type;
     char *form;
     char *form;
-} streamform[] = {
-    {MT_IO,  "LLL"},
-    {MT_CPU, "ccccc"},
-    {MT_MEM, "lllll"},
-    {MT_IF,  "llllllllll"},
-    {MT_PF,  "LLLLLLLLLLLLLLLLLLLLLL"},
-    {MT_EOT, ""}
+}      streamform[] = {
+    { MT_IO, "LLL" },
+    { MT_CPU, "ccccc" },
+    { MT_MEM, "lllll" },
+    { MT_IF, "llllllllll" },
+    { MT_PF, "LLLLLLLLLLLLLLLLLLLLLL" },
+    { MT_DEBUG, "llllllllllllllllllll" },
+    { MT_EOT, "" }
 };
 };
 
 
 struct {
 struct {
     int type;
     int type;
     int token;
     int token;
-} streamtoken[] = {
-    {MT_IO,  LXT_IO},
-    {MT_CPU, LXT_CPU},
-    {MT_MEM, LXT_MEM},
-    {MT_IF,  LXT_IF},
-    {MT_PF,  LXT_PF},
-    {MT_EOT, LXT_BADTOKEN}
+}      streamtoken[] = {
+    { MT_IO, LXT_IO },
+    { MT_CPU, LXT_CPU },
+    { MT_MEM, LXT_MEM },
+    { MT_IF, LXT_IF },
+    { MT_PF, LXT_PF },
+    { MT_DEBUG, LXT_DEBUG },
+    { MT_EOT, LXT_BADTOKEN }
 };
 };
 /* parallel crc32 table */
 /* parallel crc32 table */
-u_int32_t 
+u_int32_t
 crc32_table[256];
 crc32_table[256];
 
 
-
 /* Convert lexical entities to stream entities */
 /* Convert lexical entities to stream entities */
 const int 
 const int 
 token2type(const int token)
 token2type(const int token)
 {
 {
     int i;
     int i;
 
 
-    for (i=0; streamtoken[i].type < MT_EOT; i++) 
-	if (streamtoken[i].token == token) 
+    for (i = 0; streamtoken[i].type < MT_EOT; i++)
+	if (streamtoken[i].token == token)
 	    return streamtoken[i].type;
 	    return streamtoken[i].type;
 
 
-    fatal("%s:%d: internal error: token (%d) could not be translated into a stream type", 
+    fatal("%s:%d: internal error: token (%d) could not be translated into a stream type",
 	  __FILE__, __LINE__, token);
 	  __FILE__, __LINE__, token);
 
 
     /* NOT REACHED */
     /* NOT REACHED */
@@ -138,11 +140,11 @@ type2str(const int streamtype)
 {
 {
     int i;
     int i;
 
 
-    for (i=0; streamtoken[i].type < MT_EOT; i++) 
-	if (streamtoken[i].type == streamtype) 
+    for (i = 0; streamtoken[i].type < MT_EOT; i++)
+	if (streamtoken[i].type == streamtype)
 	    return parse_opcode(streamtoken[i].token);
 	    return parse_opcode(streamtoken[i].token);
 
 
-    fatal("%s:%d: internal error: type (%d) could not be translated into ascii representation", 
+    fatal("%s:%d: internal error: type (%d) could not be translated into ascii representation",
 	  __FILE__, __LINE__, streamtype);
 	  __FILE__, __LINE__, streamtype);
 
 
     /* NOT REACHED */
     /* NOT REACHED */
@@ -150,7 +152,7 @@ type2str(const int streamtype)
 }
 }
 /* Return the maximum lenght of the ascii representation of type <type> */
 /* Return the maximum lenght of the ascii representation of type <type> */
 int 
 int 
-strlentype(int type) 
+strlentype(int type)
 {
 {
     int i = 0;
     int i = 0;
     int sum = 0;
     int sum = 0;
@@ -166,13 +168,13 @@ strlenvar(char var)
 {
 {
     int i;
     int i;
 
 
-    for (i=0; streamvar[i].type > '\0'; i++)
+    for (i = 0; streamvar[i].type > '\0'; i++)
 	if (streamvar[i].type == var)
 	if (streamvar[i].type == var)
 	    return streamvar[i].strlen;
 	    return streamvar[i].strlen;
-    
-    fatal("%s:%d: internal error: type spefication for stream var '%c' not found", 
+
+    fatal("%s:%d: internal error: type spefication for stream var '%c' not found",
 	  __FILE__, __LINE__, var);
 	  __FILE__, __LINE__, var);
-    
+
     /* NOT REACHED */
     /* NOT REACHED */
     return 0;
     return 0;
 }
 }
@@ -182,13 +184,13 @@ bytelenvar(char var)
 {
 {
     int i;
     int i;
 
 
-    for (i=0; streamvar[i].type > '\0'; i++)
+    for (i = 0; streamvar[i].type > '\0'; i++)
 	if (streamvar[i].type == var)
 	if (streamvar[i].type == var)
 	    return streamvar[i].bytelen;
 	    return streamvar[i].bytelen;
-    
-    fatal("%s:%d: internal error: type spefication for stream var '%c' not found", 
+
+    fatal("%s:%d: internal error: type spefication for stream var '%c' not found",
 	  __FILE__, __LINE__, var);
 	  __FILE__, __LINE__, var);
-    
+
     /* NOT REACHED */
     /* NOT REACHED */
     return 0;
     return 0;
 }
 }
@@ -198,13 +200,13 @@ formatstrvar(char var)
 {
 {
     int i;
     int i;
 
 
-    for (i=0; streamvar[i].type > '\0'; i++)
+    for (i = 0; streamvar[i].type > '\0'; i++)
 	if (streamvar[i].type == var)
 	if (streamvar[i].type == var)
 	    return streamvar[i].strformat;
 	    return streamvar[i].strformat;
-    
-    fatal("%s:%d: internal error: type spefication for stream var '%c' not found", 
+
+    fatal("%s:%d: internal error: type spefication for stream var '%c' not found",
 	  __FILE__, __LINE__, var);
 	  __FILE__, __LINE__, var);
-    
+
     /* NOT REACHED */
     /* NOT REACHED */
     return "";
     return "";
 }
 }
@@ -214,29 +216,30 @@ rrdstrvar(char var)
 {
 {
     int i;
     int i;
 
 
-    for (i=0; streamvar[i].type > '\0'; i++)
+    for (i = 0; streamvar[i].type > '\0'; i++)
 	if (streamvar[i].type == var)
 	if (streamvar[i].type == var)
 	    return streamvar[i].rrdformat;
 	    return streamvar[i].rrdformat;
-    
+
     fatal("internal error: type spefication for stream var '%c' not found", var);
     fatal("internal error: type spefication for stream var '%c' not found", var);
-    
+
     /* NOT REACHED */
     /* NOT REACHED */
     return "";
     return "";
 }
 }
 /* Check whether <extra> more bytes fit in <maxlen> when we are already at <start> */
 /* Check whether <extra> more bytes fit in <maxlen> when we are already at <start> */
 int 
 int 
-checklen(int maxlen, int current, int extra) 
+checklen(int maxlen, int current, int extra)
 {
 {
     if ((current + extra) < maxlen) {
     if ((current + extra) < maxlen) {
 	return 0;
 	return 0;
-    } else {
+    }
+    else {
 	warning("buffer overflow: max=%d, current=%d, extra=%d",
 	warning("buffer overflow: max=%d, current=%d, extra=%d",
 		maxlen, current, extra);
 		maxlen, current, extra);
 	return 1;
 	return 1;
     }
     }
 }
 }
 int 
 int 
-setheader(char *buf, struct symonpacketheader *hph) 
+setheader(char *buf, struct symonpacketheader *hph)
 {
 {
     struct symonpacketheader nph;
     struct symonpacketheader nph;
     char *p;
     char *p;
@@ -248,37 +251,45 @@ setheader(char *buf, struct symonpacketheader *hph)
 
 
     p = buf;
     p = buf;
 
 
-    bcopy(&nph.crc, p, sizeof(u_int32_t)); p += sizeof(u_int32_t);
-    bcopy(&nph.timestamp, p, sizeof(u_int64_t)); p += sizeof(u_int64_t);
-    bcopy(&nph.length, p, sizeof(u_int16_t)); p += sizeof(u_int16_t);
-    bcopy(&nph.symon_version, p, sizeof(u_int8_t)); p += sizeof(u_int8_t);
+    bcopy(&nph.crc, p, sizeof(u_int32_t));
+    p += sizeof(u_int32_t);
+    bcopy(&nph.timestamp, p, sizeof(u_int64_t));
+    p += sizeof(u_int64_t);
+    bcopy(&nph.length, p, sizeof(u_int16_t));
+    p += sizeof(u_int16_t);
+    bcopy(&nph.symon_version, p, sizeof(u_int8_t));
+    p += sizeof(u_int8_t);
 
 
     return (p - buf);
     return (p - buf);
 }
 }
-int
+int 
 getheader(char *buf, struct symonpacketheader *hph)
 getheader(char *buf, struct symonpacketheader *hph)
 {
 {
     char *p;
     char *p;
 
 
     p = buf;
     p = buf;
 
 
-    bcopy(p, &hph->crc, sizeof(u_int32_t)); p += sizeof(u_int32_t);
-    bcopy(p, &hph->timestamp, sizeof(u_int64_t)); p += sizeof(u_int64_t);
-    bcopy(p, &hph->length, sizeof(u_int16_t)); p += sizeof(u_int16_t);
-    bcopy(p, &hph->symon_version, sizeof(u_int8_t)); p += sizeof(u_int8_t);
+    bcopy(p, &hph->crc, sizeof(u_int32_t));
+    p += sizeof(u_int32_t);
+    bcopy(p, &hph->timestamp, sizeof(u_int64_t));
+    p += sizeof(u_int64_t);
+    bcopy(p, &hph->length, sizeof(u_int16_t));
+    p += sizeof(u_int16_t);
+    bcopy(p, &hph->symon_version, sizeof(u_int8_t));
+    p += sizeof(u_int8_t);
 
 
     hph->timestamp = ntohq(hph->timestamp);
     hph->timestamp = ntohq(hph->timestamp);
     hph->crc = ntohl(hph->crc);
     hph->crc = ntohl(hph->crc);
     hph->length = ntohs(hph->length);
     hph->length = ntohs(hph->length);
-    
+
     return (p - buf);
     return (p - buf);
 }
 }
-/* 
+/*
  * Pack multiple arguments of a MT_TYPE into a network order bytestream.
  * Pack multiple arguments of a MT_TYPE into a network order bytestream.
- * snpack returns the number of bytes actually stored.  
+ * snpack returns the number of bytes actually stored.
  */
  */
 int 
 int 
-snpack(char *buf, int maxlen, char *id, int type, ...)
+snpack(char *buf, int maxlen, char *id, int type,...)
 {
 {
     va_list ap;
     va_list ap;
     u_int16_t b;
     u_int16_t b;
@@ -294,32 +305,36 @@ snpack(char *buf, int maxlen, char *id, int type, ...)
 	return 0;
 	return 0;
     }
     }
 
 
-    if ( maxlen < 2 ) {
+    if (maxlen < 2) {
 	fatal("%s:%d: maxlen too small", __FILE__, __LINE__);
 	fatal("%s:%d: maxlen too small", __FILE__, __LINE__);
-    } else {
+    }
+    else {
 	buf[offset++] = type & 0xff;
 	buf[offset++] = type & 0xff;
     }
     }
 
 
     if (id) {
     if (id) {
 	if ((strlen(id) + 1) >= maxlen) {
 	if ((strlen(id) + 1) >= maxlen) {
 	    return 0;
 	    return 0;
-	} else {
-	    strncpy(&buf[offset], id, maxlen-1);
+	}
+	else {
+	    strncpy(&buf[offset], id, maxlen - 1);
 	    offset += strlen(id);
 	    offset += strlen(id);
 	}
 	}
     }
     }
     buf[offset++] = '\0';
     buf[offset++] = '\0';
-	        	    
+
     va_start(ap, type);
     va_start(ap, type);
-    while (streamform[type].form[i] != '\0'){
+    while (streamform[type].form[i] != '\0') {
 	/* check for buffer overflow */
 	/* check for buffer overflow */
 	if (checklen(maxlen, offset, bytelenvar(streamform[type].form[i])))
 	if (checklen(maxlen, offset, bytelenvar(streamform[type].form[i])))
 	    return offset;
 	    return offset;
-	
-	/* all values smaller than 32 bytes are transferred using ints on the
-           stack. This is to ensure that we get the correct value, if the
-           compiler decided to upgrade our short to a 32bit int. -- cheers
-           dhartmei@ */
+
+	/*
+	 * all values smaller than 32 bytes are transferred using ints on the
+	 * stack. This is to ensure that we get the correct value, if the
+	 * compiler decided to upgrade our short to a 32bit int. -- cheers
+	 * dhartmei@
+	 */
 	switch (streamform[type].form[i]) {
 	switch (streamform[type].form[i]) {
 	case 'b':
 	case 'b':
 	    b = va_arg(ap, int);
 	    b = va_arg(ap, int);
@@ -340,14 +355,14 @@ snpack(char *buf, int maxlen, char *id, int type, ...)
 	    offset += sizeof(u_int16_t);
 	    offset += sizeof(u_int16_t);
 	    break;
 	    break;
 
 
-	case 'l': 
+	case 'l':
 	    l = va_arg(ap, u_int32_t);
 	    l = va_arg(ap, u_int32_t);
 	    l = htonl(l);
 	    l = htonl(l);
 	    bcopy(&l, buf + offset, sizeof(u_int32_t));
 	    bcopy(&l, buf + offset, sizeof(u_int32_t));
 	    offset += sizeof(u_int32_t);
 	    offset += sizeof(u_int32_t);
 	    break;
 	    break;
 
 
-	case 'L': 
+	case 'L':
 	    q = va_arg(ap, u_int64_t);
 	    q = va_arg(ap, u_int64_t);
 	    q = htonq(q);
 	    q = htonq(q);
 	    bcopy(&q, buf + offset, sizeof(u_int64_t));
 	    bcopy(&q, buf + offset, sizeof(u_int64_t));
@@ -364,25 +379,25 @@ snpack(char *buf, int maxlen, char *id, int type, ...)
 
 
     return offset;
     return offset;
 }
 }
-/* 
+/*
  * Unpack a packedstream in buf into a struct packetstream. Returns the number
  * Unpack a packedstream in buf into a struct packetstream. Returns the number
- * of bytes actually read.  
- * 
+ * of bytes actually read.
+ *
  * Note that this function does "automatic" bounds checking; it uses a
  * Note that this function does "automatic" bounds checking; it uses a
  * description of the packedstream (streamform) to parse the actual bytes. This
  * description of the packedstream (streamform) to parse the actual bytes. This
  * description corresponds to the amount of bytes that will fit inside the
  * description corresponds to the amount of bytes that will fit inside the
  * packedstream structure.  */
  * packedstream structure.  */
 int 
 int 
-sunpack(char *buf, struct packedstream *ps)
+sunpack(char *buf, struct packedstream * ps)
 {
 {
     char *in, *out;
     char *in, *out;
-    int i=0;
+    int i = 0;
     int type;
     int type;
     u_int16_t s;
     u_int16_t s;
     u_int16_t c;
     u_int16_t c;
     u_int32_t l;
     u_int32_t l;
     u_int64_t q;
     u_int64_t q;
-    
+
     bzero(ps, sizeof(struct packedstream));
     bzero(ps, sizeof(struct packedstream));
 
 
     in = buf;
     in = buf;
@@ -396,53 +411,54 @@ sunpack(char *buf, struct packedstream *ps)
     in++;
     in++;
     if ((*in) != '\0') {
     if ((*in) != '\0') {
 	strncpy(ps->args, in, sizeof(ps->args));
 	strncpy(ps->args, in, sizeof(ps->args));
-	ps->args[sizeof(ps->args)-1]='\0';
+	ps->args[sizeof(ps->args) - 1] = '\0';
 	in += strlen(ps->args);
 	in += strlen(ps->args);
-    } else {
+    }
+    else {
 	ps->args[0] = '\0';
 	ps->args[0] = '\0';
     }
     }
 
 
     in++;
     in++;
 
 
-    out = (char *)(&ps->data);
+    out = (char *) (&ps->data);
 
 
     while (streamform[type].form[i] != '\0') {
     while (streamform[type].form[i] != '\0') {
 	switch (streamform[type].form[i]) {
 	switch (streamform[type].form[i]) {
 	case 'b':
 	case 'b':
-	    bcopy((void *)in, (void *)out, sizeof(u_int8_t));
+	    bcopy((void *) in, (void *) out, sizeof(u_int8_t));
 	    in++;
 	    in++;
 	    out++;
 	    out++;
 	    break;
 	    break;
 
 
 	case 'c':
 	case 'c':
-	    bcopy((void *)in, &c, sizeof(u_int16_t));
+	    bcopy((void *) in, &c, sizeof(u_int16_t));
 	    c = ntohs(c);
 	    c = ntohs(c);
-	    bcopy(&c, (void *)out, sizeof(u_int16_t));
-	    in  += sizeof(u_int16_t);
+	    bcopy(&c, (void *) out, sizeof(u_int16_t));
+	    in += sizeof(u_int16_t);
 	    out += sizeof(u_int16_t);
 	    out += sizeof(u_int16_t);
 	    break;
 	    break;
 
 
 	case 's':
 	case 's':
-	    bcopy((void *)in, &s, sizeof(u_int16_t));
+	    bcopy((void *) in, &s, sizeof(u_int16_t));
 	    s = ntohs(s);
 	    s = ntohs(s);
-	    bcopy(&s, (void *)out, sizeof(u_int16_t));
-	    in  += sizeof(u_int16_t);
+	    bcopy(&s, (void *) out, sizeof(u_int16_t));
+	    in += sizeof(u_int16_t);
 	    out += sizeof(u_int16_t);
 	    out += sizeof(u_int16_t);
 	    break;
 	    break;
 
 
-	case 'l': 
-	    bcopy((void *)in, &l, sizeof(u_int32_t));
+	case 'l':
+	    bcopy((void *) in, &l, sizeof(u_int32_t));
 	    l = ntohl(l);
 	    l = ntohl(l);
-	    bcopy(&l, (void *)out, sizeof(u_int32_t));
-	    in  += sizeof(u_int32_t);
+	    bcopy(&l, (void *) out, sizeof(u_int32_t));
+	    in += sizeof(u_int32_t);
 	    out += sizeof(u_int32_t);
 	    out += sizeof(u_int32_t);
 	    break;
 	    break;
 
 
-	case 'L': 
-	    bcopy((void *)in, &q, sizeof(u_int64_t));
+	case 'L':
+	    bcopy((void *) in, &q, sizeof(u_int64_t));
 	    q = ntohq(q);
 	    q = ntohq(q);
-	    bcopy(&q, (void *)out, sizeof(u_int64_t));
-	    in  += sizeof(u_int64_t);
+	    bcopy(&q, (void *) out, sizeof(u_int64_t));
+	    in += sizeof(u_int64_t);
 	    out += sizeof(u_int64_t);
 	    out += sizeof(u_int64_t);
 	    break;
 	    break;
 
 
@@ -456,7 +472,7 @@ sunpack(char *buf, struct packedstream *ps)
 }
 }
 /* Get the RRD or 'pretty' ascii representation of packedstream */
 /* Get the RRD or 'pretty' ascii representation of packedstream */
 int 
 int 
-ps2strn(struct packedstream *ps, char *buf, const int maxlen, int pretty)
+ps2strn(struct packedstream * ps, char *buf, const int maxlen, int pretty)
 {
 {
     float f;
     float f;
     u_int16_t b;
     u_int16_t b;
@@ -464,19 +480,19 @@ ps2strn(struct packedstream *ps, char *buf, const int maxlen, int pretty)
     u_int16_t c;
     u_int16_t c;
     u_int64_t q;
     u_int64_t q;
     u_int32_t l;
     u_int32_t l;
-    int i=0;
+    int i = 0;
     char *formatstr;
     char *formatstr;
     char *in, *out;
     char *in, *out;
     char vartype;
     char vartype;
-    
-    in = (char *)(&ps->data);
-    out = (char *)buf;
+
+    in = (char *) (&ps->data);
+    out = (char *) buf;
 
 
     while ((vartype = streamform[ps->type].form[i]) != '\0') {
     while ((vartype = streamform[ps->type].form[i]) != '\0') {
 	/* check buffer overflow */
 	/* check buffer overflow */
-	if (checklen(maxlen, (out-buf), strlenvar(vartype)))
+	if (checklen(maxlen, (out - buf), strlenvar(vartype)))
 	    return 0;
 	    return 0;
-	
+
 	switch (pretty) {
 	switch (pretty) {
 	case PS2STR_PRETTY:
 	case PS2STR_PRETTY:
 	    formatstr = formatstrvar(vartype);
 	    formatstr = formatstrvar(vartype);
@@ -492,33 +508,33 @@ ps2strn(struct packedstream *ps, char *buf, const int maxlen, int pretty)
 	switch (vartype) {
 	switch (vartype) {
 	case 'b':
 	case 'b':
 	    bcopy(in, &b, sizeof(u_int8_t));
 	    bcopy(in, &b, sizeof(u_int8_t));
-	    snprintf(out, strlenvar(vartype), formatstr, b); 
+	    snprintf(out, strlenvar(vartype), formatstr, b);
 	    in++;
 	    in++;
-	    break; 
+	    break;
 
 
 	case 'c':
 	case 'c':
 	    bcopy(in, &c, sizeof(u_int16_t));
 	    bcopy(in, &c, sizeof(u_int16_t));
-	    f = (float)c / 10.0;
-	    snprintf(out, strlenvar(vartype), formatstr, f); 
-	    in  += sizeof(u_int16_t);
+	    f = (float) c / 10.0;
+	    snprintf(out, strlenvar(vartype), formatstr, f);
+	    in += sizeof(u_int16_t);
 	    break;
 	    break;
 
 
 	case 's':
 	case 's':
 	    bcopy(in, &s, sizeof(u_int16_t));
 	    bcopy(in, &s, sizeof(u_int16_t));
-	    snprintf(out, strlenvar(vartype), formatstr, s); 
-	    in  += sizeof(u_int16_t);
+	    snprintf(out, strlenvar(vartype), formatstr, s);
+	    in += sizeof(u_int16_t);
 	    break;
 	    break;
 
 
-	case 'l': 
+	case 'l':
 	    bcopy(in, &l, sizeof(u_int32_t));
 	    bcopy(in, &l, sizeof(u_int32_t));
-	    snprintf(out, strlenvar(vartype), formatstr, l); 
-	    in  += sizeof(u_int32_t);
+	    snprintf(out, strlenvar(vartype), formatstr, l);
+	    in += sizeof(u_int32_t);
 	    break;
 	    break;
 
 
-	case 'L': 
+	case 'L':
 	    bcopy(in, &q, sizeof(u_int64_t));
 	    bcopy(in, &q, sizeof(u_int64_t));
-	    snprintf(out, strlenvar(vartype), formatstr, q); 
-	    in  += sizeof(u_int64_t);
+	    snprintf(out, strlenvar(vartype), formatstr, q);
+	    in += sizeof(u_int64_t);
 	    break;
 	    break;
 
 
 	default:
 	default:
@@ -538,18 +554,18 @@ create_stream(int type, char *args)
     if (type < 0 || type >= MT_EOT)
     if (type < 0 || type >= MT_EOT)
 	fatal("%s:%d: internal error: stream type unknown", __FILE__, __LINE__);
 	fatal("%s:%d: internal error: stream type unknown", __FILE__, __LINE__);
 
 
-    p = (struct stream *)xmalloc(sizeof(struct stream));
+    p = (struct stream *) xmalloc(sizeof(struct stream));
     bzero(p, sizeof(struct stream));
     bzero(p, sizeof(struct stream));
     p->type = type;
     p->type = type;
 
 
     if (args != NULL)
     if (args != NULL)
 	p->args = xstrdup(args);
 	p->args = xstrdup(args);
-    
+
     return p;
     return p;
 }
 }
 /* Find the stream handle in a source */
 /* Find the stream handle in a source */
 struct stream *
 struct stream *
-find_source_stream(struct source *source, int type, char *args) 
+find_source_stream(struct source * source, int type, char *args)
 {
 {
     struct stream *p;
     struct stream *p;
 
 
@@ -557,8 +573,8 @@ find_source_stream(struct source *source, int type, char *args)
 	return NULL;
 	return NULL;
 
 
     SLIST_FOREACH(p, &source->sl, streams) {
     SLIST_FOREACH(p, &source->sl, streams) {
-	if ((p->type == type) 
-	    && (((void *)args != (void *)p != NULL) 
+	if ((p->type == type)
+	    && (((void *) args != (void *) p != NULL)
 		&& strncmp(args, p->args, _POSIX2_LINE_MAX) == 0))
 		&& strncmp(args, p->args, _POSIX2_LINE_MAX) == 0))
 	    return p;
 	    return p;
     }
     }
@@ -567,7 +583,7 @@ find_source_stream(struct source *source, int type, char *args)
 }
 }
 /* Add a stream to a source */
 /* Add a stream to a source */
 struct stream *
 struct stream *
-add_source_stream(struct source *source, int type, char *args) 
+add_source_stream(struct source * source, int type, char *args)
 {
 {
     struct stream *p;
     struct stream *p;
 
 
@@ -585,7 +601,7 @@ add_source_stream(struct source *source, int type, char *args)
 }
 }
 /* Find a stream in a mux */
 /* Find a stream in a mux */
 struct stream *
 struct stream *
-find_mux_stream(struct mux *mux, int type, char *args) 
+find_mux_stream(struct mux * mux, int type, char *args)
 {
 {
     struct stream *p;
     struct stream *p;
 
 
@@ -593,8 +609,8 @@ find_mux_stream(struct mux *mux, int type, char *args)
 	return NULL;
 	return NULL;
 
 
     SLIST_FOREACH(p, &mux->sl, streams) {
     SLIST_FOREACH(p, &mux->sl, streams) {
-	if ((p->type == type) 
-	    && (((void *)args != (void *)p != NULL) 
+	if ((p->type == type)
+	    && (((void *) args != (void *) p != NULL)
 		&& strncmp(args, p->args, _POSIX2_LINE_MAX) == 0))
 		&& strncmp(args, p->args, _POSIX2_LINE_MAX) == 0))
 	    return p;
 	    return p;
     }
     }
@@ -603,7 +619,7 @@ find_mux_stream(struct mux *mux, int type, char *args)
 }
 }
 /* Add a stream to a mux */
 /* Add a stream to a mux */
 struct stream *
 struct stream *
-add_mux_stream(struct mux *mux, int type, char *args) 
+add_mux_stream(struct mux * mux, int type, char *args)
 {
 {
     struct stream *p;
     struct stream *p;
 
 
@@ -621,7 +637,7 @@ add_mux_stream(struct mux *mux, int type, char *args)
 }
 }
 /* Find a source by name in a sourcelist */
 /* Find a source by name in a sourcelist */
 struct source *
 struct source *
-find_source(struct sourcelist *sol, char *name) 
+find_source(struct sourcelist * sol, char *name)
 {
 {
     struct source *p;
     struct source *p;
 
 
@@ -629,8 +645,8 @@ find_source(struct sourcelist *sol, char *name)
 	return NULL;
 	return NULL;
 
 
     SLIST_FOREACH(p, sol, sources) {
     SLIST_FOREACH(p, sol, sources) {
-	if (((void *)name != (void *)p != NULL) 
-	    && strncmp(name, p->name, _POSIX2_LINE_MAX) == 0)
+	if (((void *) name != (void *) p != NULL)
+	    && strncmp(name, p->addr, _POSIX2_LINE_MAX) == 0)
 	    return p;
 	    return p;
     }
     }
 
 
@@ -638,7 +654,7 @@ find_source(struct sourcelist *sol, char *name)
 }
 }
 /* Find a source by ip in a sourcelist */
 /* Find a source by ip in a sourcelist */
 struct source *
 struct source *
-find_source_ip(struct sourcelist *sol, u_int32_t ip) 
+find_source_sockaddr(struct sourcelist * sol, struct sockaddr * addr)
 {
 {
     struct source *p;
     struct source *p;
 
 
@@ -646,7 +662,7 @@ find_source_ip(struct sourcelist *sol, u_int32_t ip)
 	return NULL;
 	return NULL;
 
 
     SLIST_FOREACH(p, sol, sources) {
     SLIST_FOREACH(p, sol, sources) {
-	if (p->ip == ip)
+	if (cmpsock_addr((struct sockaddr *) & p->sockaddr, addr))
 	    return p;
 	    return p;
     }
     }
 
 
@@ -654,9 +670,9 @@ find_source_ip(struct sourcelist *sol, u_int32_t ip)
 }
 }
 /* Add a source with to a sourcelist */
 /* Add a source with to a sourcelist */
 struct source *
 struct source *
-add_source(struct sourcelist *sol, char *name)
+add_source(struct sourcelist * sol, char *name)
 {
 {
-    struct source* p;
+    struct source *p;
 
 
     if (sol == NULL)
     if (sol == NULL)
 	return NULL;
 	return NULL;
@@ -664,16 +680,17 @@ add_source(struct sourcelist *sol, char *name)
     if (find_source(sol, name) != NULL)
     if (find_source(sol, name) != NULL)
 	return NULL;
 	return NULL;
 
 
-    p = (struct source *)xmalloc(sizeof(struct source));
+    p = (struct source *) xmalloc(sizeof(struct source));
     bzero(p, sizeof(struct source));
     bzero(p, sizeof(struct source));
-    p->name = xstrdup(name);
+    p->addr = xstrdup(name);
+
     SLIST_INSERT_HEAD(sol, p, sources);
     SLIST_INSERT_HEAD(sol, p, sources);
 
 
     return p;
     return p;
 }
 }
 /* Find a mux by name in a muxlist */
 /* Find a mux by name in a muxlist */
 struct mux *
 struct mux *
-find_mux(struct muxlist *mul, char *name) 
+find_mux(struct muxlist * mul, char *name)
 {
 {
     struct mux *p;
     struct mux *p;
 
 
@@ -681,7 +698,7 @@ find_mux(struct muxlist *mul, char *name)
 	return NULL;
 	return NULL;
 
 
     SLIST_FOREACH(p, mul, muxes) {
     SLIST_FOREACH(p, mul, muxes) {
-	if (((void *)name != (void *)p != NULL) 
+	if (((void *) name != (void *) p != NULL)
 	    && strncmp(name, p->name, _POSIX2_LINE_MAX) == 0)
 	    && strncmp(name, p->name, _POSIX2_LINE_MAX) == 0)
 	    return p;
 	    return p;
     }
     }
@@ -690,9 +707,9 @@ find_mux(struct muxlist *mul, char *name)
 }
 }
 /* Add a mux to a muxlist */
 /* Add a mux to a muxlist */
 struct mux *
 struct mux *
-add_mux(struct muxlist *mul, char *name)
+add_mux(struct muxlist * mul, char *name)
 {
 {
-    struct mux* p;
+    struct mux *p;
 
 
     if (mul == NULL)
     if (mul == NULL)
 	return NULL;
 	return NULL;
@@ -700,16 +717,17 @@ add_mux(struct muxlist *mul, char *name)
     if (find_mux(mul, name) != NULL)
     if (find_mux(mul, name) != NULL)
 	return NULL;
 	return NULL;
 
 
-    p = (struct mux *)xmalloc(sizeof(struct mux));
+    p = (struct mux *) xmalloc(sizeof(struct mux));
     bzero(p, sizeof(struct mux));
     bzero(p, sizeof(struct mux));
     p->name = xstrdup(name);
     p->name = xstrdup(name);
     SLIST_INSERT_HEAD(mul, p, muxes);
     SLIST_INSERT_HEAD(mul, p, muxes);
+    SLIST_INIT(&p->sol);
 
 
     return p;
     return p;
 }
 }
 /* Rename a mux */
 /* Rename a mux */
 struct mux *
 struct mux *
-rename_mux(struct muxlist *mul, struct mux *mux, char *name)
+rename_mux(struct muxlist * mul, struct mux * mux, char *name)
 {
 {
     if (mul == NULL || mux == NULL)
     if (mul == NULL || mux == NULL)
 	return NULL;
 	return NULL;
@@ -725,61 +743,77 @@ rename_mux(struct muxlist *mul, struct mux *mux, char *name)
     return mux;
     return mux;
 }
 }
 void 
 void 
-free_muxlist(struct muxlist *mul) 
+free_muxlist(struct muxlist * mul)
 {
 {
     struct mux *p, *np;
     struct mux *p, *np;
+    int i;
 
 
     if (mul == NULL || SLIST_EMPTY(mul))
     if (mul == NULL || SLIST_EMPTY(mul))
 	return;
 	return;
 
 
     p = SLIST_FIRST(mul);
     p = SLIST_FIRST(mul);
 
 
-    while ( p ) {
+    while (p) {
 	np = SLIST_NEXT(p, muxes);
 	np = SLIST_NEXT(p, muxes);
 
 
-	if (p->name != NULL) xfree(p->name);
+	if (p->name != NULL)
+	    xfree(p->name);
+	if (p->addr != NULL)
+	    xfree(p->addr);
+	if (p->port != NULL)
+	    xfree(p->port);
+
 	close(p->clientsocket);
 	close(p->clientsocket);
-	close(p->symonsocket);
+	close(p->symuxsocket);
+	for (i = 0; i < AF_MAX; i++)
+	    if (p->symonsocket[i])
+		close(p->symonsocket[i]);
+
 	free_streamlist(&p->sl);
 	free_streamlist(&p->sl);
+	free_sourcelist(&p->sol);
 	xfree(p);
 	xfree(p);
 
 
 	p = np;
 	p = np;
     }
     }
 }
 }
 void 
 void 
-free_streamlist(struct streamlist *sl) 
+free_streamlist(struct streamlist * sl)
 {
 {
     struct stream *p, *np;
     struct stream *p, *np;
 
 
     if (sl == NULL || SLIST_EMPTY(sl))
     if (sl == NULL || SLIST_EMPTY(sl))
 	return;
 	return;
-    
+
     p = SLIST_FIRST(sl);
     p = SLIST_FIRST(sl);
 
 
-    while ( p ) {
+    while (p) {
 	np = SLIST_NEXT(p, streams);
 	np = SLIST_NEXT(p, streams);
 
 
-	if (p->args != NULL) xfree(p->args);
-	if (p->file != NULL) xfree(p->file);
+	if (p->args != NULL)
+	    xfree(p->args);
+	if (p->file != NULL)
+	    xfree(p->file);
 	xfree(p);
 	xfree(p);
 
 
 	p = np;
 	p = np;
     }
     }
 }
 }
 void 
 void 
-free_sourcelist(struct sourcelist *sol) 
+free_sourcelist(struct sourcelist * sol)
 {
 {
     struct source *p, *np;
     struct source *p, *np;
 
 
     if (sol == NULL || SLIST_EMPTY(sol))
     if (sol == NULL || SLIST_EMPTY(sol))
 	return;
 	return;
-    
+
     p = SLIST_FIRST(sol);
     p = SLIST_FIRST(sol);
 
 
-    while ( p ) {
+    while (p) {
 	np = SLIST_NEXT(p, sources);
 	np = SLIST_NEXT(p, sources);
 
 
-	if (p->name != NULL) xfree(p->name);
+	if (p->addr != NULL)
+	    xfree(p->addr);
+
 	free_streamlist(&p->sl);
 	free_streamlist(&p->sl);
 	xfree(p);
 	xfree(p);
 
 
@@ -788,19 +822,20 @@ free_sourcelist(struct sourcelist *sol)
 }
 }
 /* Calculate maximum buffer space needed for a single symon hit */
 /* Calculate maximum buffer space needed for a single symon hit */
 int 
 int 
-calculate_churnbuffer(struct sourcelist *sol) { 
-    struct source *source; 
-    struct stream *stream; 
+calculate_churnbuffer(struct sourcelist * sol)
+{
+    struct source *source;
+    struct stream *stream;
     int prefixlen;
     int prefixlen;
     int maxlen;
     int maxlen;
-    int len; 
+    int len;
     int n;
     int n;
-    
+
     /* determine length of a timestamp + ip as strings */
     /* determine length of a timestamp + ip as strings */
-    prefixlen = (sizeof(time_t)*3) + strlen(":") + 15 + strlen(":");
-    
-    len = n = 0; 
-    source = NULL; 
+    prefixlen = (sizeof(time_t) * 3) + strlen(":") + 15 + strlen(":");
+
+    len = n = 0;
+    source = NULL;
     stream = NULL;
     stream = NULL;
     maxlen = 0;
     maxlen = 0;
     /* determine maximum string size for a single source */
     /* determine maximum string size for a single source */
@@ -812,7 +847,8 @@ calculate_churnbuffer(struct sourcelist *sol) {
 	    len += strlentype(stream->type);
 	    len += strlentype(stream->type);
 	    n++;
 	    n++;
 	}
 	}
-	if (len > maxlen) maxlen = len;
+	if (len > maxlen)
+	    maxlen = len;
     }
     }
     return maxlen;
     return maxlen;
 }
 }
@@ -820,9 +856,9 @@ calculate_churnbuffer(struct sourcelist *sol) {
 u_int32_t
 u_int32_t
 crc32(const void *buf, unsigned int len)
 crc32(const void *buf, unsigned int len)
 {
 {
-    u_int8_t  *p;
+    u_int8_t *p;
     u_int32_t crc;
     u_int32_t crc;
-    
+
     crc = 0xffffffff;
     crc = 0xffffffff;
     for (p = (u_int8_t *) buf; len > 0; ++p, --len)
     for (p = (u_int8_t *) buf; len > 0; ++p, --len)
 	crc = (crc << 8) ^ crc32_table[(crc >> 24) ^ *p];
 	crc = (crc << 8) ^ crc32_table[(crc >> 24) ^ *p];
@@ -830,7 +866,7 @@ crc32(const void *buf, unsigned int len)
     return ~crc;
     return ~crc;
 }
 }
 /* Init table for CRC32 */
 /* Init table for CRC32 */
-void
+void 
 init_crc32()
 init_crc32()
 {
 {
     unsigned int i, j;
     unsigned int i, j;

+ 86 - 62
symon/lib/data.h

@@ -1,4 +1,4 @@
-/* $Id: data.h,v 1.16 2002/09/14 15:56:18 dijkstra Exp $ */
+/* $Id: data.h,v 1.17 2002/11/29 10:46:59 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -56,48 +56,48 @@
 #define ntohq(n) (n)
 #define ntohq(n) (n)
 #else
 #else
 static inline u_int64_t
 static inline u_int64_t
-htonq (u_int64_t v)
+       htonq(u_int64_t v)
 {
 {
-    return (u_int64_t)htonl(v) << 32 | htonl(v >> 32);
+    return (u_int64_t) htonl(v) << 32 | htonl(v >> 32);
 }
 }
 static inline u_int64_t
 static inline u_int64_t
-ntohq (u_int64_t v) 
+       ntohq(u_int64_t v)
 {
 {
-    return (u_int64_t)ntohl(v) << 32 | ntohl(v >> 32);
+    return (u_int64_t) ntohl(v) << 32 | ntohl(v >> 32);
 }
 }
 #endif
 #endif
 
 
-/* Symon packet version 
+/* Symon packet version
  * version 1:
  * version 1:
  * symon_version:timestamp:length:crc:n*packedstream
  * symon_version:timestamp:length:crc:n*packedstream
- * 
+ *
  * Note that the data portion is limited. The current (31/03/2002) largest
  * Note that the data portion is limited. The current (31/03/2002) largest
  * streamtype (if) needs 42 bytes without arguments. My _POSIX2_LINE_MAX is 2k,
  * streamtype (if) needs 42 bytes without arguments. My _POSIX2_LINE_MAX is 2k,
- * so that works out to about 38 packedstreams in a single symon packet.  
+ * so that works out to about 38 packedstreams in a single symon packet.
  */
  */
 #define SYMON_PACKET_VER  1
 #define SYMON_PACKET_VER  1
 
 
 /* Sending structures over the network is dangerous as the compiler might have
 /* Sending structures over the network is dangerous as the compiler might have
  * added extra padding between items. symonpacketheader below is therefore also
  * added extra padding between items. symonpacketheader below is therefore also
  * marshalled and demarshalled via snpack and sunpack. The actual values are
  * marshalled and demarshalled via snpack and sunpack. The actual values are
- * copied out of memory into this structure one by one. 
+ * copied out of memory into this structure one by one.
  */
  */
 struct symonpacketheader {
 struct symonpacketheader {
-	u_int64_t timestamp;
-	u_int32_t crc;
-	u_int16_t length;
-	u_int8_t symon_version;
-	u_int8_t reserved;
+    u_int64_t timestamp;
+    u_int32_t crc;
+    u_int16_t length;
+    u_int8_t symon_version;
+    u_int8_t reserved;
 };
 };
 
 
 struct symonpacket {
 struct symonpacket {
     struct symonpacketheader header;
     struct symonpacketheader header;
     char data[_POSIX2_LINE_MAX];
     char data[_POSIX2_LINE_MAX];
-};  
-  
+};
+
 /* The difference between a stream and a packed stream:
 /* The difference between a stream and a packed stream:
- * - A stream ties stream information to a file. 
- * - A packed stream is the measured data itself 
+ * - A stream ties stream information to a file.
+ * - A packed stream is the measured data itself
  *
  *
  * A stream is meta data describing properties, a packed stream is the data itself.
  * A stream is meta data describing properties, a packed stream is the data itself.
  */
  */
@@ -110,9 +110,8 @@ struct stream {
 SLIST_HEAD(streamlist, stream);
 SLIST_HEAD(streamlist, stream);
 
 
 struct source {
 struct source {
-    char *name;
-    u_int32_t ip;
-    u_int16_t port;
+    char *addr;
+    struct sockaddr_storage sockaddr;
     struct streamlist sl;
     struct streamlist sl;
     SLIST_ENTRY(source) sources;
     SLIST_ENTRY(source) sources;
 };
 };
@@ -120,15 +119,17 @@ SLIST_HEAD(sourcelist, source);
 
 
 struct mux {
 struct mux {
     char *name;
     char *name;
+    char *addr;
+    char *port;
+    struct sourcelist sol;
     int offset;
     int offset;
-    int clientsocket;
-    int symonsocket;
+    int clientsocket;		/* symux; incoming tcp connections */
+    int symonsocket[AF_MAX];	/* symux; incoming symon data */
+    int symuxsocket;		/* symon; outgoing data to mux */
     struct symonpacket packet;
     struct symonpacket packet;
-    struct sockaddr_in sockaddr;
+    struct sockaddr_storage sockaddr;
     struct streamlist sl;
     struct streamlist sl;
     u_int32_t senderr;
     u_int32_t senderr;
-    u_int32_t ip;
-    u_int16_t port;
     SLIST_ENTRY(mux) muxes;
     SLIST_ENTRY(mux) muxes;
 };
 };
 SLIST_HEAD(muxlist, mux);
 SLIST_HEAD(muxlist, mux);
@@ -143,54 +144,55 @@ SLIST_HEAD(muxlist, mux);
 #define MT_MEM    2
 #define MT_MEM    2
 #define MT_IF     3
 #define MT_IF     3
 #define MT_PF     4
 #define MT_PF     4
-#define MT_EOT    5
+#define MT_DEBUG  5
+#define MT_EOT    6
 
 
-/* NOTE: struct packetstream
- *
+/*
  * Unpacking of incoming packets is done via a packedstream structure. This
  * Unpacking of incoming packets is done via a packedstream structure. This
  * structure defines the maximum amount of data that can be contained in a
  * structure defines the maximum amount of data that can be contained in a
  * single network representation of a stream. It is used internally for sizing
  * single network representation of a stream. It is used internally for sizing
  * only. Although the union members are here, they could also read u_int64_t[4]
  * only. Although the union members are here, they could also read u_int64_t[4]
  * with io, for instance.
  * with io, for instance.
  */
  */
-#define SYMON_PS_ARGLEN    16
+#define SYMON_UNKMUX   "<unknown mux>"	/* mux nodes without host addr */
+#define SYMON_PS_ARGLEN    16	/* maximum argument length */
 struct packedstream {
 struct packedstream {
     int type;
     int type;
     int padding;
     int padding;
     char args[SYMON_PS_ARGLEN];
     char args[SYMON_PS_ARGLEN];
     union {
     union {
 	struct symonpacketheader header;
 	struct symonpacketheader header;
-	struct { 
+	struct {
 	    u_int64_t mtotal_transfers;
 	    u_int64_t mtotal_transfers;
 	    u_int64_t mtotal_seeks;
 	    u_int64_t mtotal_seeks;
 	    u_int64_t mtotal_bytes;
 	    u_int64_t mtotal_bytes;
-	} ps_io;
+	}      ps_io;
 	struct {
 	struct {
 	    u_int16_t muser;
 	    u_int16_t muser;
 	    u_int16_t mnice;
 	    u_int16_t mnice;
 	    u_int16_t msystem;
 	    u_int16_t msystem;
 	    u_int16_t minterrupt;
 	    u_int16_t minterrupt;
 	    u_int16_t midle;
 	    u_int16_t midle;
-	} ps_cpu;
+	}      ps_cpu;
 	struct {
 	struct {
-	    u_int32_t mreal_active; 
+	    u_int32_t mreal_active;
 	    u_int32_t mreal_total;
 	    u_int32_t mreal_total;
 	    u_int32_t mfree;
 	    u_int32_t mfree;
 	    u_int32_t mswap_used;
 	    u_int32_t mswap_used;
 	    u_int32_t mswap_total;
 	    u_int32_t mswap_total;
-	} ps_mem;
+	}      ps_mem;
 	struct {
 	struct {
 	    u_int32_t mipackets;
 	    u_int32_t mipackets;
 	    u_int32_t mopackets;
 	    u_int32_t mopackets;
-	    u_int32_t mibytes; 
+	    u_int32_t mibytes;
 	    u_int32_t mobytes;
 	    u_int32_t mobytes;
-	    u_int32_t mimcasts; 
+	    u_int32_t mimcasts;
 	    u_int32_t momcasts;
 	    u_int32_t momcasts;
-	    u_int32_t mierrors; 
+	    u_int32_t mierrors;
 	    u_int32_t moerrors;
 	    u_int32_t moerrors;
 	    u_int32_t mcolls;
 	    u_int32_t mcolls;
 	    u_int32_t mdrops;
 	    u_int32_t mdrops;
-	} ps_if;
+	}      ps_if;
 	struct {
 	struct {
 	    u_int64_t bytes_v4_in;
 	    u_int64_t bytes_v4_in;
 	    u_int64_t bytes_v4_out;
 	    u_int64_t bytes_v4_out;
@@ -214,35 +216,57 @@ struct packedstream {
 	    u_int64_t counters_short;
 	    u_int64_t counters_short;
 	    u_int64_t counters_normalize;
 	    u_int64_t counters_normalize;
 	    u_int64_t counters_memory;
 	    u_int64_t counters_memory;
-	} ps_pf;
-    } data;
+	}      ps_pf;
+	struct {
+	    u_int32_t debug0;
+	    u_int32_t debug1;
+	    u_int32_t debug2;
+	    u_int32_t debug3;
+	    u_int32_t debug4;
+	    u_int32_t debug5;
+	    u_int32_t debug6;
+	    u_int32_t debug7;
+	    u_int32_t debug8;
+	    u_int32_t debug9;
+	    u_int32_t debug10;
+	    u_int32_t debug11;
+	    u_int32_t debug12;
+	    u_int32_t debug13;
+	    u_int32_t debug14;
+	    u_int32_t debug15;
+	    u_int32_t debug16;
+	    u_int32_t debug17;
+	    u_int32_t debug18;
+	    u_int32_t debug19;
+	}      ps_debug;
+    }     data;
 };
 };
 
 
 /* prototypes */
 /* prototypes */
 __BEGIN_DECLS
 __BEGIN_DECLS
-const char    *type2str(const int);
-const int      token2type(const int);
-int            calculate_churnbuffer(struct sourcelist *);
-int            getheader(char *, struct symonpacketheader *);
-int            ps2strn(struct packedstream *, char *, int, int);
-int            setheader(char *, struct symonpacketheader *);
-int            snpack(char *, int, char*, int, ...);
-int            strlentype(int);
-int            sunpack(char *, struct packedstream *);
-struct mux    *add_mux(struct muxlist *, char *);
-struct mux    *find_mux(struct muxlist *, char *);
-struct mux *   rename_mux(struct muxlist *, struct mux *, char *);
+const char *type2str(const int);
+const int token2type(const int);
+int calculate_churnbuffer(struct sourcelist *);
+int getheader(char *, struct symonpacketheader *);
+int ps2strn(struct packedstream *, char *, int, int);
+int setheader(char *, struct symonpacketheader *);
+int snpack(char *, int, char *, int,...);
+int strlentype(int);
+int sunpack(char *, struct packedstream *);
+struct mux *add_mux(struct muxlist *, char *);
+struct mux *find_mux(struct muxlist *, char *);
+struct mux *rename_mux(struct muxlist *, struct mux *, char *);
 struct source *add_source(struct sourcelist *, char *);
 struct source *add_source(struct sourcelist *, char *);
 struct source *find_source(struct sourcelist *, char *);
 struct source *find_source(struct sourcelist *, char *);
-struct source *find_source_ip(struct sourcelist *, u_int32_t);
+struct source *find_source_sockaddr(struct sourcelist *, struct sockaddr *);
 struct stream *add_mux_stream(struct mux *, int, char *);
 struct stream *add_mux_stream(struct mux *, int, char *);
-struct stream *add_source_stream(struct source *, int, char *); 
-struct stream *find_mux_stream(struct mux *,  int, char *);
+struct stream *add_source_stream(struct source *, int, char *);
+struct stream *find_mux_stream(struct mux *, int, char *);
 struct stream *find_source_stream(struct source *, int, char *);
 struct stream *find_source_stream(struct source *, int, char *);
-u_int32_t      crc32(const void*, unsigned int);
-void           free_muxlist(struct muxlist *);
-void           free_sourcelist(struct sourcelist *);
-void           free_streamlist(struct streamlist *);
-void           init_crc32();
+u_int32_t crc32(const void *, unsigned int);
+void free_muxlist(struct muxlist *);
+void free_sourcelist(struct sourcelist *);
+void free_streamlist(struct streamlist *);
+void init_crc32();
 __END_DECLS
 __END_DECLS
-#endif /*_SYMON_LIB_DATA_H*/
+#endif				/* _SYMON_LIB_DATA_H */

+ 32 - 29
symon/lib/error.c

@@ -1,4 +1,4 @@
-/* $Id: error.c,v 1.9 2002/09/14 15:56:18 dijkstra Exp $ */
+/* $Id: error.c,v 1.10 2002/11/29 10:50:29 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -40,35 +40,37 @@
 #include "error.h"
 #include "error.h"
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
-void output_message(int, char *, va_list); 
+void output_message(int, char *, va_list);
 __END_DECLS
 __END_DECLS
 
 
 int flag_daemon = 0;
 int flag_daemon = 0;
 int flag_debug = 0;
 int flag_debug = 0;
 
 
-enum { SYMON_LOG_FATAL, 
-       SYMON_LOG_WARNING,
-       SYMON_LOG_INFO,
-       SYMON_LOG_DEBUG } loglevels;
+enum {
+    SYMON_LOG_FATAL,
+    SYMON_LOG_WARNING,
+    SYMON_LOG_INFO,
+    SYMON_LOG_DEBUG
+}    loglevels;
 
 
 struct {
 struct {
     int type;
     int type;
     int priority;
     int priority;
     char *errtxt;
     char *errtxt;
     FILE *stream;
     FILE *stream;
-} logmapping[] = {
-    {SYMON_LOG_FATAL,   LOG_ERR,     "fatal",   stderr},
-    {SYMON_LOG_WARNING, LOG_WARNING, "warning", stderr},
-    {SYMON_LOG_INFO,    LOG_INFO,    "",        stdout},
-    {SYMON_LOG_DEBUG,   LOG_DEBUG,   "debug",   stdout},
-    {-1,              0,           "",        NULL}
+}      logmapping[] = {
+    { SYMON_LOG_FATAL, LOG_ERR, "fatal", stderr },
+    { SYMON_LOG_WARNING, LOG_WARNING, "warning", stderr },
+    { SYMON_LOG_INFO, LOG_INFO, "", stdout },
+    { SYMON_LOG_DEBUG, LOG_DEBUG, "debug", stdout },
+    { -1, 0, "", NULL }
 };
 };
-/* 
- * Internal helper that actually outputs every 
- * (fatal|warning|info|debug) message 
+/*
+ * Internal helper that actually outputs every
+ * (fatal|warning|info|debug) message
  */
  */
-void
-output_message(int level, char *fmt, va_list args) 
+void 
+output_message(int level, char *fmt, va_list args)
 {
 {
     char msgbuf[_POSIX2_LINE_MAX];
     char msgbuf[_POSIX2_LINE_MAX];
     int loglevel;
     int loglevel;
@@ -77,7 +79,7 @@ output_message(int level, char *fmt, va_list args)
 	return;
 	return;
 
 
     vsnprintf(msgbuf, sizeof(msgbuf), fmt, args);
     vsnprintf(msgbuf, sizeof(msgbuf), fmt, args);
-    
+
     for (loglevel = 0; logmapping[loglevel].type != -1; loglevel++) {
     for (loglevel = 0; logmapping[loglevel].type != -1; loglevel++) {
 	if (logmapping[loglevel].type == level)
 	if (logmapping[loglevel].type == level)
 	    break;
 	    break;
@@ -89,11 +91,13 @@ output_message(int level, char *fmt, va_list args)
 
 
     if (flag_daemon) {
     if (flag_daemon) {
 	syslog(logmapping[loglevel].priority, msgbuf);
 	syslog(logmapping[loglevel].priority, msgbuf);
-    } else {
+    }
+    else {
 	if (strlen(logmapping[loglevel].errtxt) > 0) {
 	if (strlen(logmapping[loglevel].errtxt) > 0) {
-	    fprintf(logmapping[loglevel].stream, "%s: %s\n", 
+	    fprintf(logmapping[loglevel].stream, "%s: %s\n",
 		    logmapping[loglevel].errtxt, msgbuf);
 		    logmapping[loglevel].errtxt, msgbuf);
-	} else 
+	}
+	else
 	    fprintf(logmapping[loglevel].stream, "%s\n", msgbuf);
 	    fprintf(logmapping[loglevel].stream, "%s\n", msgbuf);
 
 
 	fflush(logmapping[loglevel].stream);
 	fflush(logmapping[loglevel].stream);
@@ -101,18 +105,18 @@ output_message(int level, char *fmt, va_list args)
 }
 }
 /* Output error and exit */
 /* Output error and exit */
 __dead void 
 __dead void 
-fatal(char *fmt, ...)
+fatal(char *fmt,...)
 {
 {
     va_list ap;
     va_list ap;
     va_start(ap, fmt);
     va_start(ap, fmt);
     output_message(SYMON_LOG_FATAL, fmt, ap);
     output_message(SYMON_LOG_FATAL, fmt, ap);
     va_end(ap);
     va_end(ap);
-        
-    exit( 1 );
+
+    exit(1);
 }
 }
 /* Warn and continue */
 /* Warn and continue */
 void 
 void 
-warning(char *fmt, ...)
+warning(char *fmt,...)
 {
 {
     va_list ap;
     va_list ap;
     va_start(ap, fmt);
     va_start(ap, fmt);
@@ -121,7 +125,7 @@ warning(char *fmt, ...)
 }
 }
 /* Inform and continue */
 /* Inform and continue */
 void 
 void 
-info(char *fmt, ...)
+info(char *fmt,...)
 {
 {
     va_list ap;
     va_list ap;
     va_start(ap, fmt);
     va_start(ap, fmt);
@@ -129,12 +133,11 @@ info(char *fmt, ...)
     va_end(ap);
     va_end(ap);
 }
 }
 /* Debug statements only */
 /* Debug statements only */
-void
-debug(char *fmt, ...)
+void 
+debug(char *fmt,...)
 {
 {
     va_list ap;
     va_list ap;
     va_start(ap, fmt);
     va_start(ap, fmt);
     output_message(SYMON_LOG_DEBUG, fmt, ap);
     output_message(SYMON_LOG_DEBUG, fmt, ap);
     va_end(ap);
     va_end(ap);
 }
 }
-

+ 6 - 6
symon/lib/error.h

@@ -1,4 +1,4 @@
-/* $Id: error.h,v 1.6 2002/09/14 15:56:18 dijkstra Exp $ */
+/* $Id: error.h,v 1.7 2002/11/29 10:50:29 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -40,10 +40,10 @@ extern int flag_debug;
 extern int flag_daemon;
 extern int flag_daemon;
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
-__dead void fatal(char *, ...);
-void        warning(char *, ...);
-void        info(char *, ...);
-void        debug(char *, ...);
+__dead void fatal(char *,...);
+void warning(char *,...);
+void info(char *,...);
+void debug(char *,...);
 __END_DECLS
 __END_DECLS
 
 
-#endif /*_SYMON_LIB_ERROR_H*/
+#endif				/* _SYMON_LIB_ERROR_H */

+ 60 - 54
symon/lib/lex.c

@@ -1,4 +1,4 @@
-/* $Id: lex.c,v 1.13 2002/10/25 15:24:31 dijkstra Exp $ */
+/* $Id: lex.c,v 1.14 2002/11/29 10:44:21 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -39,11 +39,11 @@
  *
  *
  * Usage:
  * Usage:
  *
  *
- *    l = open_lex(filename); 
+ *    l = open_lex(filename);
  *    while (lex_nexttoken(l)) {
  *    while (lex_nexttoken(l)) {
  *       use l->token, l->op, l->value
  *       use l->token, l->op, l->value
  *    }
  *    }
- *    close_lex(l); 
+ *    close_lex(l);
  */
  */
 
 
 #include <sys/types.h>
 #include <sys/types.h>
@@ -61,16 +61,16 @@
 static struct {
 static struct {
     const char *name;
     const char *name;
     int opcode;
     int opcode;
-} keywords[] = {
+}      keywords[] = {
     { "{", LXT_BEGIN },
     { "{", LXT_BEGIN },
     { "}", LXT_END },
     { "}", LXT_END },
     { "(", LXT_OPEN },
     { "(", LXT_OPEN },
     { ")", LXT_CLOSE },
     { ")", LXT_CLOSE },
     { ",", LXT_COMMA },
     { ",", LXT_COMMA },
-    { ":", LXT_COLON },
     { "accept", LXT_ACCEPT },
     { "accept", LXT_ACCEPT },
     { "cpu", LXT_CPU },
     { "cpu", LXT_CPU },
     { "datadir", LXT_DATADIR },
     { "datadir", LXT_DATADIR },
+    { "debug", LXT_DEBUG },
     { "if", LXT_IF },
     { "if", LXT_IF },
     { "in", LXT_IN },
     { "in", LXT_IN },
     { "io", LXT_IO },
     { "io", LXT_IO },
@@ -85,7 +85,7 @@ static struct {
     { "write", LXT_WRITE },
     { "write", LXT_WRITE },
     { NULL, 0 }
     { NULL, 0 }
 };
 };
-#define KW_OPS "{},():"
+#define KW_OPS "{},()"
 
 
 /* Return the number of the token pointed to by cp or LXT_BADTOKEN */
 /* Return the number of the token pointed to by cp or LXT_BADTOKEN */
 int 
 int 
@@ -96,16 +96,16 @@ parse_token(const char *cp)
     for (i = 0; keywords[i].name; i++)
     for (i = 0; keywords[i].name; i++)
 	if (strcasecmp(cp, keywords[i].name) == 0)
 	if (strcasecmp(cp, keywords[i].name) == 0)
 	    return keywords[i].opcode;
 	    return keywords[i].opcode;
-        
+
     return LXT_BADTOKEN;
     return LXT_BADTOKEN;
 }
 }
 /* Return the ascii representation of an opcode */
 /* Return the ascii representation of an opcode */
-const char* 
+const char *
 parse_opcode(const int op)
 parse_opcode(const int op)
 {
 {
     u_int i;
     u_int i;
-    
-    for (i=0; keywords[i].name; i++)
+
+    for (i = 0; keywords[i].name; i++)
 	if (keywords[i].opcode == op)
 	if (keywords[i].opcode == op)
 	    return keywords[i].name;
 	    return keywords[i].name;
 
 
@@ -113,30 +113,32 @@ parse_opcode(const int op)
 }
 }
 /* Read a line and increase buffer if needed */
 /* Read a line and increase buffer if needed */
 int 
 int 
-lex_readline(struct lex *l)
+lex_readline(struct lex * l)
 {
 {
     char *bp;
     char *bp;
 
 
     bp = l->buffer;
     bp = l->buffer;
 
 
     if (l->buffer) {
     if (l->buffer) {
-	if ((l->curpos < l->endpos) && 
+	if ((l->curpos < l->endpos) &&
 	    ((l->bsize - l->endpos) < _POSIX2_LINE_MAX)) {
 	    ((l->bsize - l->endpos) < _POSIX2_LINE_MAX)) {
 	    l->bsize += _POSIX2_LINE_MAX;
 	    l->bsize += _POSIX2_LINE_MAX;
 	    l->buffer = xrealloc(l->buffer, l->bsize);
 	    l->buffer = xrealloc(l->buffer, l->bsize);
 	    bp = l->buffer;
 	    bp = l->buffer;
 	    bp += l->endpos;
 	    bp += l->endpos;
-	} else {
+	}
+	else {
 	    l->curpos = 0;
 	    l->curpos = 0;
 	    l->endpos = 0;
 	    l->endpos = 0;
 	}
 	}
-    } else {
+    }
+    else {
 	l->bsize = _POSIX2_LINE_MAX;
 	l->bsize = _POSIX2_LINE_MAX;
 	l->buffer = xmalloc(l->bsize);
 	l->buffer = xmalloc(l->bsize);
 	bp = l->buffer;
 	bp = l->buffer;
     }
     }
-    
-    if (!fgets(bp, (l->buffer+l->bsize)-bp, l->fh))
+
+    if (!fgets(bp, (l->buffer + l->bsize) - bp, l->fh))
 	return 0;
 	return 0;
     else {
     else {
 	l->endpos += strlen(bp) - 1;
 	l->endpos += strlen(bp) - 1;
@@ -145,19 +147,19 @@ lex_readline(struct lex *l)
 }
 }
 /* Copy char out of input stream */
 /* Copy char out of input stream */
 void 
 void 
-lex_copychar(struct lex *l) 
+lex_copychar(struct lex * l)
 {
 {
-    l->token[l->tokpos]=l->buffer[l->curpos];
-    
+    l->token[l->tokpos] = l->buffer[l->curpos];
+
     if (++l->tokpos >= _POSIX2_LINE_MAX) {
     if (++l->tokpos >= _POSIX2_LINE_MAX) {
-	l->token[_POSIX2_LINE_MAX-1] = '\0';
+	l->token[_POSIX2_LINE_MAX - 1] = '\0';
 	fatal("%s:%d: parse error at '%s'", l->filename, l->cline, l->token);
 	fatal("%s:%d: parse error at '%s'", l->filename, l->cline, l->token);
 	/* NOT REACHED */
 	/* NOT REACHED */
     }
     }
 }
 }
 /* Get next char, read next line if needed */
 /* Get next char, read next line if needed */
 int 
 int 
-lex_nextchar(struct lex *l)
+lex_nextchar(struct lex * l)
 {
 {
     l->curpos++;
     l->curpos++;
 
 
@@ -165,54 +167,55 @@ lex_nextchar(struct lex *l)
 	if (!lex_readline(l))
 	if (!lex_readline(l))
 	    return 0;
 	    return 0;
 
 
-    if (l->buffer[l->curpos] == '\n') l->cline++;
-    
+    if (l->buffer[l->curpos] == '\n')
+	l->cline++;
+
     return 1;
     return 1;
 }
 }
 /* Close of current token with a '\0' */
 /* Close of current token with a '\0' */
 void 
 void 
-lex_termtoken(struct lex *l)
+lex_termtoken(struct lex * l)
 {
 {
-    l->token[l->tokpos] = l->token[_POSIX2_LINE_MAX-1] = '\0';
-    l->tokpos=0;
+    l->token[l->tokpos] = l->token[_POSIX2_LINE_MAX - 1] = '\0';
+    l->tokpos = 0;
 }
 }
 /* Unget token; the lexer allows 1 look a head. */
 /* Unget token; the lexer allows 1 look a head. */
 void 
 void 
-lex_ungettoken(struct lex *l) 
+lex_ungettoken(struct lex * l)
 {
 {
     l->unget = 1;
     l->unget = 1;
 }
 }
 /* Get the next token in lex->token. return 0 if no more tokens found. */
 /* Get the next token in lex->token. return 0 if no more tokens found. */
-int
-lex_nexttoken(struct lex *l)
+int 
+lex_nexttoken(struct lex * l)
 {
 {
     /* return same token as last time if it has been pushed back */
     /* return same token as last time if it has been pushed back */
     if (l->unget) {
     if (l->unget) {
 	l->unget = 0;
 	l->unget = 0;
 	return 1;
 	return 1;
     }
     }
-	
+
     l->op = LXT_BADTOKEN;
     l->op = LXT_BADTOKEN;
     l->value = 0;
     l->value = 0;
     l->type = LXY_UNKNOWN;
     l->type = LXY_UNKNOWN;
 
 
     /* find first non whitespace */
     /* find first non whitespace */
-    while (l->buffer[l->curpos] == ' ' || 
-	   l->buffer[l->curpos] == '\t' || 
+    while (l->buffer[l->curpos] == ' ' ||
+	   l->buffer[l->curpos] == '\t' ||
 	   l->buffer[l->curpos] == '\r' ||
 	   l->buffer[l->curpos] == '\r' ||
 	   l->buffer[l->curpos] == '\n' ||
 	   l->buffer[l->curpos] == '\n' ||
 	   l->buffer[l->curpos] == '\0' ||
 	   l->buffer[l->curpos] == '\0' ||
 	   l->buffer[l->curpos] == '#') {
 	   l->buffer[l->curpos] == '#') {
 	/* flush rest of line if comment */
 	/* flush rest of line if comment */
 	if (l->buffer[l->curpos] == '#') {
 	if (l->buffer[l->curpos] == '#') {
-	    while (l->buffer[l->curpos] != '\n') 
+	    while (l->buffer[l->curpos] != '\n')
 		if (!lex_nextchar(l))
 		if (!lex_nextchar(l))
 		    return 0;
 		    return 0;
-	} else
-	    if (!lex_nextchar(l))
-		return 0;
+	}
+	else if (!lex_nextchar(l))
+	    return 0;
     }
     }
-    
+
     l->type = LXY_STRING;
     l->type = LXY_STRING;
 
 
     /* "delimited string" */
     /* "delimited string" */
@@ -232,7 +235,7 @@ lex_nexttoken(struct lex *l)
 	lex_nextchar(l);
 	lex_nextchar(l);
 	return 1;
 	return 1;
     }
     }
-    
+
     /* 'delimited string' */
     /* 'delimited string' */
     if (l->buffer[l->curpos] == '\'') {
     if (l->buffer[l->curpos] == '\'') {
 	if (!lex_nextchar(l)) {
 	if (!lex_nextchar(l)) {
@@ -250,7 +253,7 @@ lex_nexttoken(struct lex *l)
 	lex_nextchar(l);
 	lex_nextchar(l);
 	return 1;
 	return 1;
     }
     }
-    
+
     /* one char keyword */
     /* one char keyword */
     if (strchr(KW_OPS, l->buffer[l->curpos])) {
     if (strchr(KW_OPS, l->buffer[l->curpos])) {
 	lex_copychar(l);
 	lex_copychar(l);
@@ -262,7 +265,7 @@ lex_nexttoken(struct lex *l)
 
 
     /* single keyword */
     /* single keyword */
     while (l->buffer[l->curpos] != ' ' &&
     while (l->buffer[l->curpos] != ' ' &&
-	   l->buffer[l->curpos] != '\t' && 
+	   l->buffer[l->curpos] != '\t' &&
 	   l->buffer[l->curpos] != '\r' &&
 	   l->buffer[l->curpos] != '\r' &&
 	   l->buffer[l->curpos] != '\n' &&
 	   l->buffer[l->curpos] != '\n' &&
 	   l->buffer[l->curpos] != '\0' &&
 	   l->buffer[l->curpos] != '\0' &&
@@ -276,20 +279,20 @@ lex_nexttoken(struct lex *l)
     l->op = parse_token(l->token);
     l->op = parse_token(l->token);
 
 
     /* number */
     /* number */
-    if (l->token[0] >= '0' && l->token[0] <= '9' ) {
+    if (l->token[0] >= '0' && l->token[0] <= '9') {
 	if (strlen(l->token) == strspn(l->token, "0123456789")) {
 	if (strlen(l->token) == strspn(l->token, "0123456789")) {
 	    l->type = LXY_NUMBER;
 	    l->type = LXY_NUMBER;
-	    l->value = strtol(l->token, NULL , 10);
+	    l->value = strtol(l->token, NULL, 10);
 	}
 	}
     }
     }
     return 1;
     return 1;
-}    
+}
 /* Create and initialize a lexical analyser */
 /* Create and initialize a lexical analyser */
 struct lex *
 struct lex *
 open_lex(const char *filename)
 open_lex(const char *filename)
 {
 {
     struct lex *l;
     struct lex *l;
-    
+
     l = xmalloc(sizeof(struct lex));
     l = xmalloc(sizeof(struct lex));
     l->buffer = NULL;
     l->buffer = NULL;
     l->cline = 1;
     l->cline = 1;
@@ -304,7 +307,7 @@ open_lex(const char *filename)
     l->value = 0;
     l->value = 0;
 
 
     if ((l->fh = fopen(l->filename, "r")) == NULL) {
     if ((l->fh = fopen(l->filename, "r")) == NULL) {
-	warning("could not open file '%s':%s", 
+	warning("could not open file '%s':%s",
 		l->filename, strerror(errno));
 		l->filename, strerror(errno));
 	xfree(l);
 	xfree(l);
 	return NULL;
 	return NULL;
@@ -315,19 +318,22 @@ open_lex(const char *filename)
 }
 }
 /* Destroy a lexical analyser */
 /* Destroy a lexical analyser */
 void 
 void 
-close_lex(struct lex *l)
+close_lex(struct lex * l)
 {
 {
-    if (l == NULL) return;
-    if (l->fh) fclose(l->fh);
-    if (l->buffer) xfree(l->buffer);
-    if (l->token) xfree(l->token);
+    if (l == NULL)
+	return;
+    if (l->fh)
+	fclose(l->fh);
+    if (l->buffer)
+	xfree(l->buffer);
+    if (l->token)
+	xfree(l->token);
     xfree(l);
     xfree(l);
 }
 }
 /* Signal a parse error */
 /* Signal a parse error */
-void
-parse_error(struct lex *l, const char *s)
+void 
+parse_error(struct lex * l, const char *s)
 {
 {
-    warning("%s:%d: expected %s (found '%.8s')", 
+    warning("%s:%d: expected %s (found '%.8s')",
 	    l->filename, l->cline, s, l->token);
 	    l->filename, l->cline, s, l->token);
 }
 }
-

+ 27 - 26
symon/lib/lex.h

@@ -1,4 +1,4 @@
-/* $Id: lex.h,v 1.13 2002/10/25 15:24:31 dijkstra Exp $ */
+/* $Id: lex.h,v 1.14 2002/11/29 10:50:29 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -32,7 +32,7 @@
 
 
 /*
 /*
  * This file defines the keyword tokens and lexer structure for the simple
  * This file defines the keyword tokens and lexer structure for the simple
- * lexical analyser. 
+ * lexical analyser.
  */
  */
 
 
 #ifndef _SYMON_LIB_LEX_H
 #ifndef _SYMON_LIB_LEX_H
@@ -47,10 +47,10 @@
 #define LXT_ACCEPT     1
 #define LXT_ACCEPT     1
 #define LXT_BEGIN      2
 #define LXT_BEGIN      2
 #define LXT_CLOSE      3
 #define LXT_CLOSE      3
-#define LXT_COLON      4
-#define LXT_COMMA      5
-#define LXT_CPU        6
-#define LXT_DATADIR    7
+#define LXT_COMMA      4
+#define LXT_CPU        5
+#define LXT_DATADIR    6
+#define LXT_DEBUG      7
 #define LXT_END        8
 #define LXT_END        8
 #define LXT_IF         9
 #define LXT_IF         9
 #define LXT_IN        10
 #define LXT_IN        10
@@ -67,30 +67,32 @@
 #define LXT_WRITE     21
 #define LXT_WRITE     21
 
 
 struct lex {
 struct lex {
-    char *buffer;          /* current line(s) */
+    char *buffer;		/* current line(s) */
     const char *filename;
     const char *filename;
     FILE *fh;
     FILE *fh;
-    char *token;           /* last token seen */
-    long value;            /* value of last token seen, if num */
-    int bsize;             /* size of buffer  */
-    int cline;             /* current lineno */
-    int curpos;            /* current position in buffer */
-    int endpos;            /* current maxpos in buffer */
-    int op;                /* opcode of token, if string */
-    int unget;             /* bool; token pushed back */
-    int tokpos;            /* current position in token buffer */
-    enum { LXY_STRING, LXY_NUMBER, LXY_UNKNOWN } 
-        type;              /* type of token in buffer */
+    char *token;		/* last token seen */
+    long value;			/* value of last token seen, if num */
+    int bsize;			/* size of buffer  */
+    int cline;			/* current lineno */
+    int curpos;			/* current position in buffer */
+    int endpos;			/* current maxpos in buffer */
+    int op;			/* opcode of token, if string */
+    int unget;			/* bool; token pushed back */
+    int tokpos;			/* current position in token buffer */
+    enum {
+	LXY_STRING, LXY_NUMBER, LXY_UNKNOWN
+    }
+         type;			/* type of token in buffer */
 };
 };
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
 struct lex *open_lex(const char *);
 struct lex *open_lex(const char *);
-void        close_lex(struct lex *);
-int         lex_nexttoken(struct lex *);
-void        lex_ungettoken(struct lex *);
-const char* parse_opcode(int);
-int         parse_token(const char *);
-void        parse_error(struct lex *, const char *);
+void close_lex(struct lex *);
+int lex_nexttoken(struct lex *);
+void lex_ungettoken(struct lex *);
+const char *parse_opcode(int);
+int parse_token(const char *);
+void parse_error(struct lex *, const char *);
 __END_DECLS
 __END_DECLS
 
 
 /* EXPECT(l,x) = next token in l must be opcode x or error.  */
 /* EXPECT(l,x) = next token in l must be opcode x or error.  */
@@ -102,5 +104,4 @@ __END_DECLS
 	}                                         \
 	}                                         \
     } while (0);
     } while (0);
 
 
-#endif /*_SYMON_LIB_LEX_H*/
-
+#endif				/* _SYMON_LIB_LEX_H */

+ 169 - 61
symon/lib/net.c

@@ -1,4 +1,4 @@
-/* $Id: net.c,v 1.6 2002/08/29 19:38:52 dijkstra Exp $ */
+/* $Id: net.c,v 1.7 2002/11/29 10:45:20 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -30,81 +30,189 @@
  *
  *
  */
  */
 
 
-#include <netdb.h>
-#include <netinet/in.h>
-#include <sys/socket.h>
-#include <arpa/inet.h>
-
 #include <sys/types.h>
 #include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
 
 
-#include <limits.h>
-#include <stdio.h>
+#include <netdb.h>
 #include <string.h>
 #include <string.h>
 
 
+#include "data.h"
+#include "error.h"
+#include "net.h"
+
 /*
 /*
- * lookup( hostname ) - hostname resolver
+ * getip( address | fqdn ) - get ip address
  *
  *
- * Lookup returns 1 if hostname could be resolved. Resolved data is
- * stored in the globals lookup_hostname, lookup_address and lookup_ip below.  
+ * getip returns 1 if address could be reworked into an ip address. Resolved
+ * data is stored in the globals res_host. The address structure res_addr is
+ * aslo filled with sockaddr information that was obtained.
  */
  */
-char lookup_hostname[_POSIX2_LINE_MAX];
-char lookup_address[_POSIX2_LINE_MAX];
-u_int32_t lookup_ip;
-
+char res_host[NI_MAXHOST];
+struct sockaddr_storage res_addr;
 int 
 int 
-lookup(char *name)
+getip(char *name)
 {
 {
-    struct in_addr addr;
-    struct hostent *host;
-    extern int h_errno;
-    char *chostname, *sptr;
-    int i, bestl, newl;
-	
-    strcpy(lookup_hostname, "unresolved.");
-    strcpy(lookup_address, "unresolved.");
-    strncat(lookup_hostname, name, (_POSIX2_LINE_MAX - 1 - sizeof("unresolved")));
-    strncat(lookup_address, name, (_POSIX2_LINE_MAX - 1 - sizeof("unresolved")));
-
-    if (4 == sscanf(name, "%4d.%4d.%4d.%4d", &i, &i, &i, &i)) {
-	addr.s_addr = inet_addr(name);
-	if (addr.s_addr == 0xffffffff) 
+    struct addrinfo hints, *res;
+    int error;
+
+    res = NULL;
+    bzero((void *) &hints, sizeof(struct addrinfo));
+
+    /* don't lookup if we have a numeric address already */
+    hints.ai_flags = AI_NUMERICHOST;
+    if (getaddrinfo(name, NULL, &hints, &res) != 0) {
+	hints.ai_flags = 0;
+	if ((error = getaddrinfo(name, NULL, &hints, &res)) < 0) {
+	    warning("getaddrinfo(%.200s): %.200s", name, gai_strerror(error));
 	    return 0;
 	    return 0;
-	    
-	host = gethostbyaddr((char *)&addr.s_addr, 4, AF_INET);
-    } else {
-	host = gethostbyname(name);
+	}
     }
     }
-    
-    if (host == NULL) {
-	return 0;
-    } else {
-	i = 0;
-	newl = 0;
-	bestl = 0;
-	sptr = (char *)(host->h_name ? host->h_name : host->h_aliases[0]);
-	chostname = NULL;
-
-	while (sptr) {
-	    newl = strlen(sptr);
-	    if (newl > bestl) {
-		bestl = newl;
-		chostname = sptr;
-	    }
 
 
-	    sptr = host->h_aliases[i++];
+    if (res && hints.ai_flags & AI_NUMERICHOST) {
+	strncpy(res_host, name, NI_MAXHOST);
+	res_host[NI_MAXHOST - 1] = 0;
+
+	cpysock(res->ai_addr, &res_addr);
+
+	freeaddrinfo(res);
+	return 1;
+    }
+    else {
+	if (res->ai_addr) {
+	    if ((error = getnameinfo(res->ai_addr, res->ai_addrlen,
+				     res_host, NI_MAXHOST,
+				     NULL, 0, NI_NUMERICHOST)) == 0) {
+		res_host[NI_MAXHOST - 1] = 0;
+
+		cpysock(res->ai_addr, &res_addr);
+
+		freeaddrinfo(res);
+		return 1;
+	    }
+	    else
+		warning("getnameinfo(%.200s): %.200s", name, gai_strerror(error));
 	}
 	}
-	
-	if (chostname)
-	    snprintf(lookup_hostname, (_POSIX2_LINE_MAX - 1), "%s", chostname);
-	
-	if (*host->h_addr_list) {
-	    lookup_ip = ntohl(*(u_int32_t *) *(char **) host->h_addr_list);
-
-	    snprintf(lookup_address, (_POSIX2_LINE_MAX - 1),"%u.%u.%u.%u", 
-		    (lookup_ip >> 24), (lookup_ip >> 16) & 0xff,
-		    (lookup_ip >> 8) & 0xff, lookup_ip & 0xff);
+	else
+	    warning("getip(%s): could not get numeric host via getaddrinfo nor getnameinfo", name);
+    }
+
+    return 0;
+}
+/*
+ * getaddr( address | fqdn, service ) - get the addrinfo structure
+ *
+ * getaddr returns a sockaddr structure in res_addr. it will only resolve
+ * the address if that is necessary.
+ */
+int 
+getaddr(char *name, char *service, int socktype, int flags)
+{
+    struct addrinfo hints, *res;
+    int error;
+
+    res = NULL;
+    bzero((void *) &hints, sizeof(hints));
+
+    hints.ai_flags = flags;
+    hints.ai_socktype = socktype;
+
+    /* don't lookup if not necessary */
+    hints.ai_flags |= AI_NUMERICHOST;
+    if (getaddrinfo(name, service, &hints, &res) != 0) {
+	hints.ai_flags = flags;
+	if ((error = getaddrinfo(name, service, &hints, &res)) < 0) {
+	    warning("getaddrinfo(%.200s): %.200s", name, gai_strerror(error));
+	    return 0;
 	}
 	}
     }
     }
 
 
+    if (res->ai_addrlen > sizeof(res_addr))
+	fatal("%s:%d: internal error: getaddr returned bigger sockaddr than expected (%d>%d)",
+	      __FILE__, __LINE__, res->ai_addrlen, sizeof(res_addr));
+
+    cpysock(res->ai_addr, &res_addr);
+
     return 1;
     return 1;
 }
 }
+void 
+cpysock(struct sockaddr * source, struct sockaddr_storage * dest)
+{
+    bzero(dest, sizeof(struct sockaddr_storage));
+    bcopy(source, dest, source->sa_len);
+}
+/*
+ * cmpsock_addr(sockaddr, sockaddr)
+ *
+ * compare if two sockaddr are talking about the same host
+ */
+int 
+cmpsock_addr(struct sockaddr * first, struct sockaddr * second)
+{
+
+    if (first == NULL || second == NULL)
+	return 0;
+
+    if ((first->sa_len != second->sa_len) ||
+	(first->sa_family != second->sa_family))
+	return 0;
+
+    if (first->sa_family == PF_INET) {
+	if (bcmp((void *) &((struct sockaddr_in *) first)->sin_addr,
+		 (void *) &((struct sockaddr_in *) second)->sin_addr,
+		 sizeof(struct in_addr)) == 0)
+	    return 1;
+
+	else
+	    return 0;
+    }
+
+    if (first->sa_family == PF_INET6) {
+	if (bcmp((void *) &((struct sockaddr_in6 *) first)->sin6_addr,
+		 (void *) &((struct sockaddr_in6 *) second)->sin6_addr,
+		 sizeof(struct in6_addr)) == 0)
+	    return 1;
+	else
+	    return 0;
+    }
+
+    /* don't know what to compare for this family */
+    return 0;
+}
+/* generate INADDR_ANY info */
+void 
+get_inaddrany_sockaddr(struct sockaddr_storage * sockaddr, int family, int socktype, char *port)
+{
+    struct addrinfo hints, *res;
+
+    bzero((void *) &hints, sizeof(struct addrinfo));
+    hints.ai_family = family;
+    hints.ai_socktype = socktype;
+    hints.ai_flags = AI_PASSIVE;
+    if (getaddrinfo(NULL, port, &hints, &res) != 0)
+	fatal("could not get inaddr address");
+    else {
+	cpysock((struct sockaddr *) res->ai_addr, sockaddr);
+	freeaddrinfo(res);
+    }
+}
+/* fill a source->sockaddr with a sockaddr for use in address compares */
+void 
+get_source_sockaddr(struct source * source)
+{
+    if (!getip(source->addr))
+	fatal("could not get address information for %s",
+	      source->addr);
+
+    cpysock((struct sockaddr *) & res_addr, &source->sockaddr);
+}
+/* fill mux->sockaddr with a udp listen sockaddr */
+void 
+get_mux_sockaddr(struct mux * mux, int socktype)
+{
+    if (getaddr(mux->addr, mux->port, socktype, AI_PASSIVE) == 0)
+	fatal("could not get address information for %s %s",
+	      mux->addr, mux->port);
+
+    cpysock((struct sockaddr *) & res_addr, &mux->sockaddr);
+}

+ 15 - 7
symon/lib/net.h

@@ -1,4 +1,4 @@
-/* $Id: net.h,v 1.7 2002/09/14 15:56:18 dijkstra Exp $ */
+/* $Id: net.h,v 1.9 2002/11/29 10:45:20 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -33,20 +33,28 @@
 #ifndef _SYMON_LIB_NET_H
 #ifndef _SYMON_LIB_NET_H
 #define _SYMON_LIB_NET_H
 #define _SYMON_LIB_NET_H
 
 
+#include <sys/queue.h>
+#include <sys/socket.h>
 #include <sys/types.h>
 #include <sys/types.h>
 
 
-#define SYMUX_PORT  2100                     /* default symux port */
-
-/* Rewrite an ipadress uint32_t as 4 comma seperated bytes */
-#define IPAS4BYTES(x) \
-        ((x) >> 24), ((x) >> 16) & 0xff, ((x) >> 8) & 0xff, (x) & 0xff
+#define SYMUX_PORT  "2100"	/* default symux port */
 
 
 extern char lookup_hostname[];
 extern char lookup_hostname[];
 extern char lookup_address[];
 extern char lookup_address[];
 extern u_int32_t lookup_ip;
 extern u_int32_t lookup_ip;
+extern char res_host[];
+extern struct sockaddr_storage res_addr;
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
+int cmpsock_addr(struct sockaddr *, struct sockaddr *);
+int getaddr(char *, char *, int, int);
+int getip(char *);
 int lookup(char *);
 int lookup(char *);
+void cpysock(struct sockaddr *, struct sockaddr_storage *);
+void get_inaddrany_sockaddr(struct sockaddr_storage *, int, int, char *);
+void get_mux_sockaddr(struct mux *, int);
+void get_source_sockaddr(struct source *);
 __END_DECLS
 __END_DECLS
 
 
-#endif /* _SYMON_LIB_NET_H */
+#endif				/* _SYMON_LIB_NET_H */
+

+ 7 - 7
symon/lib/xmalloc.c

@@ -1,4 +1,4 @@
-/* $Id: xmalloc.c,v 1.4 2002/03/31 14:27:46 dijkstra Exp $ */
+/* $Id: xmalloc.c,v 1.5 2002/11/29 10:50:29 dijkstra Exp $ */
 
 
 /*
 /*
  * Author: Tatu Ylonen <ylo@cs.hut.fi>
  * Author: Tatu Ylonen <ylo@cs.hut.fi>
@@ -24,15 +24,15 @@ void *
 xmalloc(size_t size)
 xmalloc(size_t size)
 {
 {
     void *ptr;
     void *ptr;
-    
+
     if (size == 0)
     if (size == 0)
 	fatal("xmalloc: zero size");
 	fatal("xmalloc: zero size");
-    
+
     ptr = malloc(size);
     ptr = malloc(size);
-    
+
     if (ptr == NULL)
     if (ptr == NULL)
 	fatal("xmalloc: out of memory (allocating %lu bytes)", (u_long) size);
 	fatal("xmalloc: out of memory (allocating %lu bytes)", (u_long) size);
-    
+
     return ptr;
     return ptr;
 }
 }
 
 
@@ -40,7 +40,7 @@ void *
 xrealloc(void *ptr, size_t new_size)
 xrealloc(void *ptr, size_t new_size)
 {
 {
     void *new_ptr;
     void *new_ptr;
-    
+
     if (new_size == 0)
     if (new_size == 0)
 	fatal("xrealloc: zero size");
 	fatal("xrealloc: zero size");
 
 
@@ -64,7 +64,7 @@ xfree(void *ptr)
     free(ptr);
     free(ptr);
 }
 }
 
 
-char 
+char
 *xstrdup(const char *str)
 *xstrdup(const char *str)
 {
 {
     size_t len = strlen(str) + 1;
     size_t len = strlen(str) + 1;

+ 6 - 6
symon/lib/xmalloc.h

@@ -1,4 +1,4 @@
-/* $Id: xmalloc.h,v 1.5 2002/09/14 15:56:18 dijkstra Exp $ */
+/* $Id: xmalloc.h,v 1.6 2002/11/29 10:50:29 dijkstra Exp $ */
 
 
 /*
 /*
  * Author: Tatu Ylonen <ylo@cs.hut.fi>
  * Author: Tatu Ylonen <ylo@cs.hut.fi>
@@ -21,9 +21,9 @@
 
 
 /* Like malloc and friends, but these call fatal if something breaks */
 /* Like malloc and friends, but these call fatal if something breaks */
 __BEGIN_DECLS
 __BEGIN_DECLS
-void   *xmalloc(size_t);
-void   *xrealloc(void *, size_t);
-void    xfree(void *);
-char   *xstrdup(const char *);
+void *xmalloc(size_t);
+void *xrealloc(void *, size_t);
+void xfree(void *);
+char *xstrdup(const char *);
 __END_DECLS
 __END_DECLS
-#endif /*_SYMON_LIB_XMALLOC_H*/
+#endif				/* _SYMON_LIB_XMALLOC_H */

+ 4 - 2
symon/ports/symon/Makefile

@@ -1,10 +1,10 @@
 # $OpenBSD: Makefile,v 1.1 2002/10/08 07:56:42 dhartmei Exp $
 # $OpenBSD: Makefile,v 1.1 2002/10/08 07:56:42 dhartmei Exp $
 
 
 COMMENT=		"active monitoring tool"
 COMMENT=		"active monitoring tool"
-V=			2.53
+V=			2.55
 DISTNAME=		symon-${V}
 DISTNAME=		symon-${V}
 CATEGORIES=		net sysutils
 CATEGORIES=		net sysutils
-NEED_VERSION=		1.502
+
 MASTER_SITES=		http://www.xs4all.nl/~wpd/symon/
 MASTER_SITES=		http://www.xs4all.nl/~wpd/symon/
 
 
 HOMEPAGE=		http://www.xs4all.nl/~wpd/symon/
 HOMEPAGE=		http://www.xs4all.nl/~wpd/symon/
@@ -52,4 +52,6 @@ LIB_DEPENDS=		rrd:rrdtool-*:net/rrdtool
 WRKDIST=		${WRKDIR}/symon
 WRKDIST=		${WRKDIR}/symon
 SUBST_VARS=		V
 SUBST_VARS=		V
 
 
+NO_REGRESS=		Yes
+
 .include <bsd.port.mk>
 .include <bsd.port.mk>

+ 25 - 0
symon/ports/symon/pkg/DEINSTALL

@@ -0,0 +1,25 @@
+#!/bin/sh
+# $Id: DEINSTALL,v 1.1 2002/11/29 10:59:56 dijkstra Exp $
+#
+# symon de-installation
+
+set -e
+PATH=/bin:/usr/bin:/sbin:/usr/sbin
+PREFIX=${PKG_PREFIX:-/usr/local}
+CONFIG_FILE=${SYSCONFDIR}/symon.conf
+
+if [ -e $CONFIG_FILE ]; then
+    echo
+    echo "+---------------"
+    echo "| To completely deinstall the $1 package you need to perform"
+    echo "| this step as root:"
+    echo "|"
+    echo "|           rm -f $CONFIG_FILE"
+    echo "|"
+    echo "| Do not do this if you plan on re-installing $1"
+    echo "| at some future time."
+    echo "+---------------"
+    echo
+fi
+
+exit 0

+ 2 - 2
symon/ports/symon/pkg/DEINSTALL-mon

@@ -1,12 +1,12 @@
 #!/bin/sh
 #!/bin/sh
-# $Id: DEINSTALL-mon,v 1.1 2002/10/18 12:26:28 dijkstra Exp $
+# $Id: DEINSTALL-mon,v 1.2 2002/11/29 10:50:32 dijkstra Exp $
 #
 #
 # symon de-installation
 # symon de-installation
 
 
 set -e
 set -e
 PATH=/bin:/usr/bin:/sbin:/usr/sbin
 PATH=/bin:/usr/bin:/sbin:/usr/sbin
 PREFIX=${PKG_PREFIX:-/usr/local}
 PREFIX=${PKG_PREFIX:-/usr/local}
-CONFIG_FILE=${SYSCONFDIR}/lftp.conf
+CONFIG_FILE=${SYSCONFDIR}/symon.conf
 
 
 if [ -e $CONFIG_FILE ]; then
 if [ -e $CONFIG_FILE ]; then
     echo
     echo

+ 67 - 0
symon/ports/symon/pkg/INSTALL

@@ -0,0 +1,67 @@
+#!/bin/sh
+# $Id: INSTALL,v 1.1 2002/11/29 10:59:56 dijkstra Exp $
+#
+# Pre/post-installation setup of symon monitor
+
+# exit on errors, use a sane path and install prefix
+#
+set -e
+PATH=/bin:/usr/bin:/sbin:/usr/sbin
+PREFIX=${PKG_PREFIX:-/usr/local}
+CONFIG_FILE=${SYSCONFDIR}/symon.conf
+SAMPLE_CONFIG_FILE=$PREFIX/share/symon/symon.conf
+
+do_notice()
+{
+    echo
+    echo "+---------------"
+    echo "| The existing $1 configuration file, $CONFIG_FILE,"
+    echo "| has NOT been changed. You may want to compare it to the"
+    echo "| current sample file, $SAMPLE_CONFIG_FILE,"
+    echo "| and update your configuration as needed."
+    echo "+---------------"
+    echo
+}
+
+do_install()
+{
+    $PREFIX/share/symon/c_config.sh 127.0.0.1 2100 > $CONFIG_FILE
+
+    echo
+    echo "+---------------"
+    echo "| The $1 configuration file, $CONFIG_FILE, has been generated by"
+    echo "| $PREFIX/share/symon/c_config.sh.  It has been filled with cpu, memory,"
+    echo "| pf, default disks and interfaces. Please review this file and change"
+    echo "| the configuration to suit your needs."
+    echo "+---------------"
+    echo 
+}
+
+# verify proper execution
+#
+if [ $# -ne 2 ]; then
+    echo "usage: $0 distname { PRE-INSTALL | POST-INSTALL }" >&2
+    exit 1
+fi
+
+# Verify/process the command
+#
+case $2 in
+    PRE-INSTALL)
+        : nothing to pre-install for this port
+        ;;
+    POST-INSTALL)
+	if [ -f $CONFIG_FILE ]; then
+	    do_notice $1
+	else
+	    do_install $1
+	fi
+        ;;
+    *)
+        echo "usage: $0 distname { PRE-INSTALL | POST-INSTALL }" >&2
+        exit 1
+        ;;
+esac
+
+exit 0
+

+ 5 - 1
symon/ports/symon/pkg/PLIST

@@ -1,4 +1,4 @@
-@comment $Id: PLIST,v 1.2 2002/10/18 12:26:28 dijkstra Exp $
+@comment $Id: PLIST,v 1.3 2002/11/08 15:39:40 dijkstra Exp $
 @comment $OpenBSD: PLIST,v 1.1 2002/10/08 07:56:42 dhartmei Exp $
 @comment $OpenBSD: PLIST,v 1.1 2002/10/08 07:56:42 dhartmei Exp $
 libexec/symon
 libexec/symon
 libexec/symux
 libexec/symux
@@ -23,5 +23,9 @@ share/symon/web/index.php
 share/symon/web/symon.css              
 share/symon/web/symon.css              
 share/symon/web/symon.png              
 share/symon/web/symon.png              
 share/symon/web/spacer.png           
 share/symon/web/spacer.png           
+share/symon/web/test_config.php
+share/symon/client/getsymonitem.pl
+share/symon/client/SymuxClient.pm
+share/symon/client/SymuxClient.0
 @dirrm share/symon/web
 @dirrm share/symon/web
 @dirrm share/symon
 @dirrm share/symon

+ 4 - 1
symon/ports/symon/pkg/PLIST-mux

@@ -1,7 +1,10 @@
-@comment $Id: PLIST-mux,v 1.2 2002/10/18 12:26:28 dijkstra Exp $
+@comment $Id: PLIST-mux,v 1.3 2002/11/08 15:39:40 dijkstra Exp $
 @comment $OpenBSD: PLIST-mux,v 1.1 2002/10/08 07:56:42 dhartmei Exp $
 @comment $OpenBSD: PLIST-mux,v 1.1 2002/10/08 07:56:42 dhartmei Exp $
 libexec/symux
 libexec/symux
 man/cat8/symux.0
 man/cat8/symux.0
 share/symon/c_smrrds.sh
 share/symon/c_smrrds.sh
 share/symon/symux.conf
 share/symon/symux.conf
+share/symon/client/getsymonitem.pl
+share/symon/client/SymuxClient.pm
+share/symon/client/SymuxClient.0
 @dirrm share/symon
 @dirrm share/symon

+ 1 - 0
symon/ports/symon/pkg/PLIST-web

@@ -16,5 +16,6 @@ share/symon/web/index.php
 share/symon/web/symon.css              
 share/symon/web/symon.css              
 share/symon/web/symon.png              
 share/symon/web/symon.png              
 share/symon/web/spacer.png           
 share/symon/web/spacer.png           
+share/symon/web/test_config.php
 @dirrm share/symon/web
 @dirrm share/symon/web
 @dirrm share/symon
 @dirrm share/symon

+ 3 - 3
symon/symon/Makefile

@@ -1,10 +1,10 @@
-# $Id: Makefile,v 1.27 2002/10/18 12:29:48 dijkstra Exp $
+# $Id: Makefile,v 1.28 2002/11/29 10:48:53 dijkstra Exp $
 .include "../Makefile.inc"
 .include "../Makefile.inc"
 
 
 LIBS=	-L../lib -lsymon
 LIBS=	-L../lib -lsymon
-SRCS=	symon.c sm_cpu.c sm_mem.c sm_if.c sm_io.c sm_pf.c readconf.c symonnet.c 
+SRCS=	symon.c sm_cpu.c sm_debug.c sm_mem.c sm_if.c sm_io.c sm_pf.c readconf.c symonnet.c 
 OBJS+=	${SRCS:R:S/$/.o/g}
 OBJS+=	${SRCS:R:S/$/.o/g}
-CFLAGS+=-DNET_INET6 -I../lib
+CFLAGS+=-I../lib
 
 
 all: symon symon.cat8
 all: symon symon.cat8
 
 

+ 2 - 2
symon/symon/c_config.sh

@@ -1,5 +1,5 @@
 #!/bin/sh
 #!/bin/sh
-# $Id: c_config.sh,v 1.1 2002/10/18 12:29:48 dijkstra Exp $
+# $Id: c_config.sh,v 1.2 2002/11/29 10:48:53 dijkstra Exp $
 #
 #
 # Create an example configuration file for symon on a host and print to stdout
 # Create an example configuration file for symon on a host and print to stdout
 
 
@@ -36,6 +36,6 @@ cat <<EOF
 #
 #
 monitor { $if 
 monitor { $if 
           $io 
           $io 
-          cpu(0), mem } stream to $host:$port
+          cpu(0), mem } stream to $host $port
 EOF
 EOF
 
 

+ 51 - 55
symon/symon/readconf.c

@@ -1,4 +1,4 @@
-/* $Id: readconf.c,v 1.11 2002/10/18 12:29:48 dijkstra Exp $ */
+/* $Id: readconf.c,v 1.12 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -32,20 +32,13 @@
 
 
 #include <sys/queue.h>
 #include <sys/queue.h>
 
 
-#include <stdarg.h>
-#include <stdio.h>
 #include <string.h>
 #include <string.h>
-#include <assert.h>
-#include <limits.h>
-#include <fcntl.h>
-#include <unistd.h>
 
 
 #include "data.h"
 #include "data.h"
 #include "error.h"
 #include "error.h"
 #include "lex.h"
 #include "lex.h"
-#include "symon.h"
 #include "net.h"
 #include "net.h"
-#include "readconf.h"
+#include "symon.h"
 #include "xmalloc.h"
 #include "xmalloc.h"
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
@@ -54,63 +47,65 @@ int read_symon_args(struct mux *, struct lex *);
 int read_monitor(struct muxlist *, struct lex *);
 int read_monitor(struct muxlist *, struct lex *);
 __END_DECLS
 __END_DECLS
 
 
+const char *default_symux_port = SYMUX_PORT;
+
 /* <hostname> (port|:|,| ) <number> */
 /* <hostname> (port|:|,| ) <number> */
-int
-read_host_port(struct muxlist *mul, struct mux *mux, struct lex *l)
+int 
+read_host_port(struct muxlist * mul, struct mux * mux, struct lex * l)
 {
 {
+    char muxname[_POSIX2_LINE_MAX];
+
     lex_nexttoken(l);
     lex_nexttoken(l);
-    if (!lookup(l->token)) {
+    if (!getip(l->token)) {
 	warning("%s:%d: could not resolve '%s'",
 	warning("%s:%d: could not resolve '%s'",
 		l->filename, l->cline, l->token);
 		l->filename, l->cline, l->token);
 	return 0;
 	return 0;
     }
     }
 
 
-    if (rename_mux(mul, mux, lookup_address) == NULL) {
-	warning("%s:%d: monitored data for host '%s' has already been specified",
-		l->filename, l->cline, lookup_address);
-	return 0;
-    }
-	
-    mux->ip = lookup_ip;
+    mux->addr = xstrdup((const char *) &res_host);
 
 
     /* check for port statement */
     /* check for port statement */
     if (!lex_nexttoken(l))
     if (!lex_nexttoken(l))
 	return 1;
 	return 1;
 
 
-    if (l->op == LXT_PORT || l->op == LXT_COLON || l->op == LXT_COMMA)
+    if (l->op == LXT_PORT || l->op == LXT_COMMA)
 	lex_nexttoken(l);
 	lex_nexttoken(l);
+
+    if (l->type != LXY_NUMBER) {
+	lex_ungettoken(l);
+	mux->port = xstrdup(default_symux_port);
+    }
     else {
     else {
-	if (l->type != LXY_NUMBER) {
-	    lex_ungettoken(l);
-	    mux->port = SYMUX_PORT;
-	    return 1;
-	}
+	mux->port = xstrdup((const char *) l->token);
     }
     }
 
 
-    if (l->type != LXY_NUMBER) {
-	parse_error(l, "<number>");
+    bzero(&muxname, sizeof(muxname));
+    snprintf(&muxname[0], sizeof(muxname), "%s %s", mux->addr, mux->port);
+    if (rename_mux(mul, mux, muxname) == NULL) {
+	warning("%s:%d: monitored data for host '%s' has already been specified",
+		l->filename, l->cline, muxname);
 	return 0;
 	return 0;
     }
     }
 
 
-    mux->port = l->value;
     return 1;
     return 1;
 }
 }
-/* parse "<cpu(arg)|mem|if(arg)|io(arg)>", end condition == "}" */
+/* parse "<cpu(arg)|mem|if(arg)|io(arg)|debug|pf>", end condition == "}" */
 int 
 int 
-read_symon_args(struct mux *mux, struct lex *l) 
+read_symon_args(struct mux * mux, struct lex * l)
 {
 {
     char sn[_POSIX2_LINE_MAX];
     char sn[_POSIX2_LINE_MAX];
     char sa[_POSIX2_LINE_MAX];
     char sa[_POSIX2_LINE_MAX];
-    int  st;
+    int st;
 
 
     EXPECT(l, LXT_BEGIN)
     EXPECT(l, LXT_BEGIN)
-    while (lex_nexttoken(l) && l->op != LXT_END) {
+	while (lex_nexttoken(l) && l->op != LXT_END) {
 	switch (l->op) {
 	switch (l->op) {
 	case LXT_CPU:
 	case LXT_CPU:
 	case LXT_IF:
 	case LXT_IF:
 	case LXT_IO:
 	case LXT_IO:
 	case LXT_MEM:
 	case LXT_MEM:
 	case LXT_PF:
 	case LXT_PF:
+	case LXT_DEBUG:
 	    st = token2type(l->op);
 	    st = token2type(l->op);
 	    strncpy(&sn[0], l->token, _POSIX2_LINE_MAX);
 	    strncpy(&sn[0], l->token, _POSIX2_LINE_MAX);
 
 
@@ -118,19 +113,20 @@ read_symon_args(struct mux *mux, struct lex *l)
 	    lex_nexttoken(l);
 	    lex_nexttoken(l);
 	    if (l->op == LXT_OPEN) {
 	    if (l->op == LXT_OPEN) {
 		lex_nexttoken(l);
 		lex_nexttoken(l);
-		if (l->op == LXT_CLOSE){
+		if (l->op == LXT_CLOSE) {
 		    parse_error(l, "<stream argument>");
 		    parse_error(l, "<stream argument>");
 		    return 0;
 		    return 0;
 		}
 		}
 		strncpy(&sa[0], l->token, _POSIX2_LINE_MAX);
 		strncpy(&sa[0], l->token, _POSIX2_LINE_MAX);
 		lex_nexttoken(l);
 		lex_nexttoken(l);
-		if (l->op != LXT_CLOSE){
+		if (l->op != LXT_CLOSE) {
 		    parse_error(l, ")");
 		    parse_error(l, ")");
 		    return 0;
 		    return 0;
 		}
 		}
-	    } else {
+	    }
+	    else {
 		lex_ungettoken(l);
 		lex_ungettoken(l);
-		sa[0]='\0';
+		sa[0] = '\0';
 	    }
 	    }
 
 
 	    if ((add_mux_stream(mux, st, sa)) == NULL) {
 	    if ((add_mux_stream(mux, st, sa)) == NULL) {
@@ -138,27 +134,27 @@ read_symon_args(struct mux *mux, struct lex *l)
 			l->filename, l->cline, sn, sa);
 			l->filename, l->cline, sn, sa);
 		return 0;
 		return 0;
 	    }
 	    }
-	    
-	    break; /* LXT_CPU/IF/IO/MEM/PF */
+
+	    break;		/* LXT_CPU/IF/IO/MEM/PF/DEBUG */
 	case LXT_COMMA:
 	case LXT_COMMA:
 	    break;
 	    break;
 	default:
 	default:
-	    parse_error(l, "{cpu|mem|if|io|pf}");
+	    parse_error(l, "{cpu|mem|if|io|pf|debug}");
 	    return 0;
 	    return 0;
 	    break;
 	    break;
 	}
 	}
     }
     }
-    
+
     return 1;
     return 1;
 }
 }
 
 
 /* parse monitor <args> stream [to] <host>:<port> */
 /* parse monitor <args> stream [to] <host>:<port> */
-int
-read_monitor(struct muxlist *mul, struct lex *l)
+int 
+read_monitor(struct muxlist * mul, struct lex * l)
 {
 {
     struct mux *mux;
     struct mux *mux;
 
 
-    mux = add_mux(mul, "<unnamed host>");
+    mux = add_mux(mul, SYMON_UNKMUX);
 
 
     /* parse cpu|mem|if|io */
     /* parse cpu|mem|if|io */
     if (!read_symon_args(mux, l))
     if (!read_symon_args(mux, l))
@@ -167,20 +163,16 @@ read_monitor(struct muxlist *mul, struct lex *l)
     /* parse stream to */
     /* parse stream to */
     EXPECT(l, LXT_STREAM);
     EXPECT(l, LXT_STREAM);
     lex_nexttoken(l);
     lex_nexttoken(l);
-    if (l->op != LXT_TO) 
+    if (l->op != LXT_TO)
 	lex_ungettoken(l);
 	lex_ungettoken(l);
 
 
     /* parse host */
     /* parse host */
-    if (!read_host_port(mul, mux, l))
-	return 0;
-    
-    return 1;
+    return read_host_port(mul, mux, l);
 }
 }
 
 
 /* Read symon.conf */
 /* Read symon.conf */
-int
-read_config_file(struct muxlist *muxlist, 
-		 const char *filename)
+int 
+read_config_file(struct muxlist * muxlist, const char *filename)
 {
 {
     struct lex *l;
     struct lex *l;
     struct mux *mux;
     struct mux *mux;
@@ -189,16 +181,16 @@ read_config_file(struct muxlist *muxlist,
 
 
     if ((l = open_lex(filename)) == NULL)
     if ((l = open_lex(filename)) == NULL)
 	return 0;
 	return 0;
-    
+
     while (lex_nexttoken(l)) {
     while (lex_nexttoken(l)) {
-    /* expecting keyword now */
+	/* expecting keyword now */
 	switch (l->op) {
 	switch (l->op) {
 	case LXT_MONITOR:
 	case LXT_MONITOR:
-	    if (!read_monitor(muxlist, l)) 
+	    if (!read_monitor(muxlist, l))
 		return 0;
 		return 0;
 	    break;
 	    break;
 	default:
 	default:
-	    parse_error(l, "monitor" );
+	    parse_error(l, "monitor");
 	    return 0;
 	    return 0;
 	    break;
 	    break;
 	}
 	}
@@ -206,6 +198,10 @@ read_config_file(struct muxlist *muxlist,
 
 
     /* sanity checks */
     /* sanity checks */
     SLIST_FOREACH(mux, muxlist, muxes) {
     SLIST_FOREACH(mux, muxlist, muxes) {
+	if (strncmp(SYMON_UNKMUX, mux->name, sizeof(SYMON_UNKMUX)) == 0) {
+	    /* mux was not initialised for some reason */
+	    return 0;
+	}
 	if (SLIST_EMPTY(&mux->sl)) {
 	if (SLIST_EMPTY(&mux->sl)) {
 	    warning("%s: no monitors selected for mux '%s'",
 	    warning("%s: no monitors selected for mux '%s'",
 		    l->filename, mux->name);
 		    l->filename, mux->name);

+ 2 - 14
symon/symon/readconf.h

@@ -1,4 +1,4 @@
-/* $Id: readconf.h,v 1.4 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: readconf.h,v 1.5 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -33,21 +33,9 @@
 #ifndef _SYMON_READCONF_H
 #ifndef _SYMON_READCONF_H
 #define _SYMON_READCONF_H
 #define _SYMON_READCONF_H
 
 
-#include <sys/cdefs.h>
-
 #include "data.h"
 #include "data.h"
-#include "lex.h"
-
-/* Monitor subsystem structure */
-struct symonm {
-    int type;
-    void  (*init)(char *);
-    char* (*get)(char *);
-};
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
 int read_config_file(struct muxlist *, const char *);
 int read_config_file(struct muxlist *, const char *);
 __END_DECLS
 __END_DECLS
-#endif /*_SYMON_READCONF_H*/
-
-
+#endif				/* _SYMON_READCONF_H */

+ 15 - 15
symon/symon/sm_cpu.c

@@ -1,7 +1,7 @@
-/* $Id: sm_cpu.c,v 1.13 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: sm_cpu.c,v 1.14 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /* The author of this code is Willem Dijkstra (wpd@xs4all.nl).
 /* The author of this code is Willem Dijkstra (wpd@xs4all.nl).
- * 
+ *
  * The percentages function was written by William LeFebvre and is part of the
  * The percentages function was written by William LeFebvre and is part of the
  * 'top' utility. His copyright statement is below.
  * 'top' utility. His copyright statement is below.
  *
  *
@@ -66,7 +66,7 @@ int percentages(int, int *, long *, long *, long *);
 __END_DECLS
 __END_DECLS
 
 
 /* Globals for this module all start with cp_ */
 /* Globals for this module all start with cp_ */
-static int cp_time_mib[] = { CTL_KERN, KERN_CPTIME };
+static int cp_time_mib[] = {CTL_KERN, KERN_CPTIME};
 static size_t cp_size;
 static size_t cp_size;
 static long cp_time[CPUSTATES];
 static long cp_time[CPUSTATES];
 static long cp_old[CPUSTATES];
 static long cp_old[CPUSTATES];
@@ -97,27 +97,27 @@ percentages(int cnt, int *out, register long *new, register long *old, long *dif
     for (i = 0; i < cnt; i++) {
     for (i = 0; i < cnt; i++) {
 	if ((change = *new - *old) < 0) {
 	if ((change = *new - *old) < 0) {
 	    /* this only happens when the counter wraps */
 	    /* this only happens when the counter wraps */
-	    change = ((unsigned int)*new-(unsigned int)*old);
-        }
+	    change = ((unsigned int) *new - (unsigned int) *old);
+	}
 	total_change += (*dp++ = change);
 	total_change += (*dp++ = change);
 	*old++ = *new++;
 	*old++ = *new++;
     }
     }
-  
+
     /* avoid divide by zero potential */
     /* avoid divide by zero potential */
     if (total_change == 0)
     if (total_change == 0)
 	total_change = 1;
 	total_change = 1;
-  
+
     /* calculate percentages based on overall change, rounding up */
     /* calculate percentages based on overall change, rounding up */
     half_total = total_change / 2l;
     half_total = total_change / 2l;
     for (i = 0; i < cnt; i++)
     for (i = 0; i < cnt; i++)
 	*out++ = ((*diffs++ * 1000 + half_total) / total_change);
 	*out++ = ((*diffs++ * 1000 + half_total) / total_change);
-  
+
     /* return the total in case the caller wants to use it */
     /* return the total in case the caller wants to use it */
     return total_change;
     return total_change;
 }
 }
 /* Prepare cpu module for use */
 /* Prepare cpu module for use */
 void 
 void 
-init_cpu(char *s) 
+init_cpu(char *s)
 {
 {
     char buf[_POSIX2_LINE_MAX];
     char buf[_POSIX2_LINE_MAX];
 
 
@@ -129,7 +129,7 @@ init_cpu(char *s)
 }
 }
 /* Get new cpu measurements */
 /* Get new cpu measurements */
 int 
 int 
-get_cpu(char *symon_buf, int maxlen, char *s) 
+get_cpu(char *symon_buf, int maxlen, char *s)
 {
 {
     int total;
     int total;
 
 
@@ -140,11 +140,11 @@ get_cpu(char *symon_buf, int maxlen, char *s)
 
 
     /* convert cp_time counts to percentages */
     /* convert cp_time counts to percentages */
     total = percentages(CPUSTATES, cp_states, cp_time, cp_old, cp_diff);
     total = percentages(CPUSTATES, cp_states, cp_time, cp_old, cp_diff);
-    
+
     return snpack(symon_buf, maxlen, s, MT_CPU,
     return snpack(symon_buf, maxlen, s, MT_CPU,
-		  cp_states[CP_USER], 
-		  cp_states[CP_NICE], 
-		  cp_states[CP_SYS], 
-		  cp_states[CP_INTR], 
+		  cp_states[CP_USER],
+		  cp_states[CP_NICE],
+		  cp_states[CP_SYS],
+		  cp_states[CP_INTR],
 		  cp_states[CP_IDLE]);
 		  cp_states[CP_IDLE]);
 }
 }

+ 80 - 0
symon/symon/sm_debug.c

@@ -0,0 +1,80 @@
+/* $Id: sm_debug.c,v 1.1 2002/11/29 10:44:18 dijkstra Exp $ */
+
+/*
+ * Copyright (c) 2001-2002 Willem Dijkstra
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ *    - Redistributions of source code must retain the above copyright
+ *      notice, this list of conditions and the following disclaimer.
+ *    - Redistributions in binary form must reproduce the above
+ *      copyright notice, this list of conditions and the following
+ *      disclaimer in the documentation and/or other materials provided
+ *      with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+ * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+
+/*
+ * Get current debug statistics from kernel and return them in symon_buf as
+ *
+ * debug0 : debug1 : ... : debug19
+ *
+ */
+
+#include <sys/param.h>
+#include <sys/sysctl.h>
+
+#include <string.h>
+
+#include "error.h"
+#include "symon.h"
+
+#define SYMON_MAXDEBUGID      20/* = CTL_DEBUG_MAXID; depends lib/data.h */
+
+/* Globals for this module start with db_ */
+int db_mib[] = {CTL_DEBUG, 0, CTL_DEBUG_VALUE};
+int db_v[SYMON_MAXDEBUGID];
+/* Prepare if module for first use */
+void 
+init_debug(char *s)
+{
+    info("started module debug(%s)", s);
+}
+/* Get debug statistics */
+int 
+get_debug(char *symon_buf, int maxlen, char *s)
+{
+    size_t len;
+    int i;
+
+    bzero((void *) db_v, sizeof(db_v));
+    len = sizeof(int);
+
+    for (i = 0; i < SYMON_MAXDEBUGID; i++) {
+	db_mib[1] = i;
+
+	sysctl(db_mib, 3, &db_v[i], &len, NULL, 0);
+    }
+
+    return snpack(symon_buf, maxlen, s, MT_DEBUG,
+		  db_v[0], db_v[1], db_v[2], db_v[3], db_v[4], db_v[5], db_v[6],
+		  db_v[7], db_v[8], db_v[9], db_v[10], db_v[11], db_v[12], db_v[13],
+		  db_v[14], db_v[15], db_v[16], db_v[17], db_v[18], db_v[19]);
+
+}

+ 18 - 20
symon/symon/sm_if.c

@@ -1,4 +1,4 @@
-/* $Id: sm_if.c,v 1.6 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: sm_if.c,v 1.7 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -35,7 +35,7 @@
  *
  *
  * ipackets : opackets : ibytes : obytes : imcasts : omcasts : ierrors :
  * ipackets : opackets : ibytes : obytes : imcasts : omcasts : ierrors :
  * oerrors : colls : drops
  * oerrors : colls : drops
- * 
+ *
  */
  */
 
 
 #include <sys/types.h>
 #include <sys/types.h>
@@ -66,42 +66,40 @@
 int if_s = -1;
 int if_s = -1;
 /* Prepare if module for first use */
 /* Prepare if module for first use */
 void 
 void 
-init_if(char *s) 
+init_if(char *s)
 {
 {
     if (if_s == -1)
     if (if_s == -1)
 	if ((if_s = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
 	if ((if_s = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
-	    fatal("%s:%d: socket failed, %.200", 
+	    fatal("%s:%d: socket failed, %.200",
 		  __FILE__, __LINE__, strerror(errno));
 		  __FILE__, __LINE__, strerror(errno));
 
 
     info("started module if(%s)", s);
     info("started module if(%s)", s);
 }
 }
 /* Get interface statistics */
 /* Get interface statistics */
 int 
 int 
-get_if(char *symon_buf, int maxlen, char *interface) 
+get_if(char *symon_buf, int maxlen, char *interface)
 {
 {
     struct ifreq ifr;
     struct ifreq ifr;
     struct if_data ifdata;
     struct if_data ifdata;
 
 
-    strncpy(ifr.ifr_name, interface, IFNAMSIZ-1);
+    strncpy(ifr.ifr_name, interface, IFNAMSIZ - 1);
     ifr.ifr_name[IFNAMSIZ - 1] = '\0';
     ifr.ifr_name[IFNAMSIZ - 1] = '\0';
-    ifr.ifr_data = (caddr_t)&ifdata;
-    
+    ifr.ifr_data = (caddr_t) & ifdata;
+
     if (ioctl(if_s, SIOCGIFDATA, &ifr)) {
     if (ioctl(if_s, SIOCGIFDATA, &ifr)) {
 	warning("if(%s) failed (ioctl error)", interface);
 	warning("if(%s) failed (ioctl error)", interface);
 	return 0;
 	return 0;
     }
     }
-    
+
     return snpack(symon_buf, maxlen, interface, MT_IF,
     return snpack(symon_buf, maxlen, interface, MT_IF,
-		  ifdata.ifi_ipackets, 
-		  ifdata.ifi_opackets, 
-		  ifdata.ifi_ibytes, 
-		  ifdata.ifi_obytes, 
-		  ifdata.ifi_imcasts, 
-		  ifdata.ifi_omcasts, 
-		  ifdata.ifi_ierrors, 
-		  ifdata.ifi_oerrors, 
-		  ifdata.ifi_collisions, 
+		  ifdata.ifi_ipackets,
+		  ifdata.ifi_opackets,
+		  ifdata.ifi_ibytes,
+		  ifdata.ifi_obytes,
+		  ifdata.ifi_imcasts,
+		  ifdata.ifi_omcasts,
+		  ifdata.ifi_ierrors,
+		  ifdata.ifi_oerrors,
+		  ifdata.ifi_collisions,
 		  ifdata.ifi_iqdrops);
 		  ifdata.ifi_iqdrops);
 }
 }
-
-

+ 14 - 14
symon/symon/sm_io.c

@@ -1,4 +1,4 @@
-/* $Id: sm_io.c,v 1.8 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: sm_io.c,v 1.9 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -32,11 +32,11 @@
 
 
 /*
 /*
  * Get current disk transfer statistics from kernel and return them in symon_buf as
  * Get current disk transfer statistics from kernel and return them in symon_buf as
- * 
+ *
  * total nr of transfers : total seeks : total bytes transferred
  * total nr of transfers : total seeks : total bytes transferred
  *
  *
  * Non re-entrant code: gets_io messes with globals r/w without a semaphore.
  * Non re-entrant code: gets_io messes with globals r/w without a semaphore.
- * 
+ *
  */
  */
 #include <sys/param.h>
 #include <sys/param.h>
 #include <sys/sysctl.h>
 #include <sys/sysctl.h>
@@ -58,14 +58,14 @@ int io_maxdks = 0;
 int io_maxstr = 0;
 int io_maxstr = 0;
 
 
 void 
 void 
-gets_io() 
+gets_io()
 {
 {
     int mib[3];
     int mib[3];
     char *p;
     char *p;
     int dks;
     int dks;
     size_t size;
     size_t size;
     size_t strsize;
     size_t strsize;
-    
+
     /* how much memory is needed */
     /* how much memory is needed */
     mib[0] = CTL_HW;
     mib[0] = CTL_HW;
     mib[1] = HW_DISKCOUNT;
     mib[1] = HW_DISKCOUNT;
@@ -79,7 +79,7 @@ gets_io()
     mib[1] = HW_DISKNAMES;
     mib[1] = HW_DISKNAMES;
     strsize = 0;
     strsize = 0;
     if (sysctl(mib, 2, NULL, &strsize, NULL, 0) < 0) {
     if (sysctl(mib, 2, NULL, &strsize, NULL, 0) < 0) {
-	fatal("%s:%d: sysctl failed: can't get hw.disknames", 
+	fatal("%s:%d: sysctl failed: can't get hw.disknames",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
     }
     }
 
 
@@ -92,7 +92,7 @@ gets_io()
 	    fatal("%s:%d: dynamic object limit (%d) exceeded for diskstat structures",
 	    fatal("%s:%d: dynamic object limit (%d) exceeded for diskstat structures",
 		  __FILE__, __LINE__, SYMON_MAX_DOBJECTS);
 		  __FILE__, __LINE__, SYMON_MAX_DOBJECTS);
 	}
 	}
-	
+
 	if (io_maxstr > SYMON_MAX_OBJSIZE) {
 	if (io_maxstr > SYMON_MAX_OBJSIZE) {
 	    fatal("%s:%d: string size exceeded (%d)",
 	    fatal("%s:%d: string size exceeded (%d)",
 		  __FILE__, __LINE__, SYMON_MAX_OBJSIZE);
 		  __FILE__, __LINE__, SYMON_MAX_OBJSIZE);
@@ -124,28 +124,28 @@ gets_io()
     io_dks = 0;
     io_dks = 0;
     while ((io_dknames[io_dks] = strsep(&p, ",")) != NULL)
     while ((io_dknames[io_dks] = strsep(&p, ",")) != NULL)
 	io_dks++;
 	io_dks++;
-}    
+}
 /* Prepare io module for first use */
 /* Prepare io module for first use */
 void 
 void 
-init_io(char *s) 
+init_io(char *s)
 {
 {
     info("started module io(%s)", s);
     info("started module io(%s)", s);
 }
 }
 /* Get new io statistics */
 /* Get new io statistics */
 int 
 int 
-get_io(char *symon_buf, int maxlen, char *disk) 
+get_io(char *symon_buf, int maxlen, char *disk)
 {
 {
     int i;
     int i;
 
 
     /* look for disk */
     /* look for disk */
-    for (i=0; i<io_dks; i++) {
-	if (strncmp(io_dknames[i], disk, 
+    for (i = 0; i < io_dks; i++) {
+	if (strncmp(io_dknames[i], disk,
 		    (io_dkstr + io_maxstr - io_dknames[i])) == 0)
 		    (io_dkstr + io_maxstr - io_dknames[i])) == 0)
 	    return snpack(symon_buf, maxlen, disk, MT_IO,
 	    return snpack(symon_buf, maxlen, disk, MT_IO,
-			  io_dkstats[i].ds_xfer, 
+			  io_dkstats[i].ds_xfer,
 			  io_dkstats[i].ds_seek,
 			  io_dkstats[i].ds_seek,
 			  io_dkstats[i].ds_bytes);
 			  io_dkstats[i].ds_bytes);
-    } 
+    }
 
 
     return 0;
     return 0;
 }
 }

+ 16 - 17
symon/symon/sm_mem.c

@@ -1,4 +1,4 @@
-/* $Id: sm_mem.c,v 1.12 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: sm_mem.c,v 1.13 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -64,10 +64,10 @@ static int me_pagesize;
 static int me_nswap;
 static int me_nswap;
 struct swapent *me_swdev = NULL;
 struct swapent *me_swdev = NULL;
 /* Prepare mem module for first use */
 /* Prepare mem module for first use */
-void
-init_mem(char *s) 
+void 
+init_mem(char *s)
 {
 {
-    me_pagesize = sysconf( _SC_PAGESIZE );
+    me_pagesize = sysconf(_SC_PAGESIZE);
     me_pageshift = 0;
     me_pageshift = 0;
     while (me_pagesize > 1) {
     while (me_pagesize > 1) {
 	me_pageshift++;
 	me_pageshift++;
@@ -79,17 +79,17 @@ init_mem(char *s)
 
 
     /* determine number of swap entries */
     /* determine number of swap entries */
     me_nswap = swapctl(SWAP_NSWAP, 0, 0);
     me_nswap = swapctl(SWAP_NSWAP, 0, 0);
-  
-    if (me_swdev) 
+
+    if (me_swdev)
 	xfree(me_swdev);
 	xfree(me_swdev);
 
 
     if (me_nswap != 0)
     if (me_nswap != 0)
-      me_swdev = xmalloc(me_nswap * sizeof(*me_swdev));
+	me_swdev = xmalloc(me_nswap * sizeof(*me_swdev));
     else
     else
-      me_swdev = NULL;
+	me_swdev = NULL;
 
 
-    if (me_swdev == NULL && me_nswap != 0) 
-	me_nswap=0; 
+    if (me_swdev == NULL && me_nswap != 0)
+	me_nswap = 0;
 
 
     info("started module mem(%s)", s);
     info("started module mem(%s)", s);
 }
 }
@@ -97,7 +97,7 @@ init_mem(char *s)
 int 
 int 
 get_mem(char *symon_buf, int maxlen, char *s)
 get_mem(char *symon_buf, int maxlen, char *s)
 {
 {
-    int i,rnswap;
+    int i, rnswap;
 
 
     if (sysctl(me_vm_mib, 2, &me_vmtotal, &me_vmsize, NULL, 0) < 0) {
     if (sysctl(me_vm_mib, 2, &me_vmtotal, &me_vmsize, NULL, 0) < 0) {
 	warning("%s:%d: sysctl failed", __FILE__, __LINE__);
 	warning("%s:%d: sysctl failed", __FILE__, __LINE__);
@@ -110,14 +110,14 @@ get_mem(char *symon_buf, int maxlen, char *s)
     me_stats[2] = pagetob(me_vmtotal.t_free);
     me_stats[2] = pagetob(me_vmtotal.t_free);
 
 
     rnswap = swapctl(SWAP_STATS, me_swdev, me_nswap);
     rnswap = swapctl(SWAP_STATS, me_swdev, me_nswap);
-    if (rnswap == -1) { 
+    if (rnswap == -1) {
 	/* A swap device may have been added; increase and retry */
 	/* A swap device may have been added; increase and retry */
-	init_mem(NULL); 
+	init_mem(NULL);
 	rnswap = swapctl(SWAP_STATS, me_swdev, me_nswap);
 	rnswap = swapctl(SWAP_STATS, me_swdev, me_nswap);
     }
     }
 
 
     me_stats[3] = me_stats[4] = 0;
     me_stats[3] = me_stats[4] = 0;
-    if (rnswap == me_nswap) { /* Read swap succesfully */
+    if (rnswap == me_nswap) {	/* Read swap succesfully */
 	/* Total things up */
 	/* Total things up */
 	for (i = 0; i < me_nswap; i++) {
 	for (i = 0; i < me_nswap; i++) {
 	    if (me_swdev[i].se_flags & SWF_ENABLE) {
 	    if (me_swdev[i].se_flags & SWF_ENABLE) {
@@ -127,8 +127,7 @@ get_mem(char *symon_buf, int maxlen, char *s)
 	}
 	}
     }
     }
 
 
-    return snpack(symon_buf, maxlen, s, MT_MEM, 
-		  me_stats[0], me_stats[1], me_stats[2], 
+    return snpack(symon_buf, maxlen, s, MT_MEM,
+		  me_stats[0], me_stats[1], me_stats[2],
 		  me_stats[3], me_stats[4]);
 		  me_stats[3], me_stats[4]);
 }
 }
-

+ 10 - 10
symon/symon/sm_pf.c

@@ -1,4 +1,4 @@
-/* $Id: sm_pf.c,v 1.3 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: sm_pf.c,v 1.4 2002/11/29 10:48:53 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2002 Daniel Hartmeier
  * Copyright (c) 2002 Daniel Hartmeier
@@ -31,7 +31,7 @@
  */
  */
 
 
 /*
 /*
- * Get current pf statistics and return them in symon_buf as 
+ * Get current pf statistics and return them in symon_buf as
  *
  *
  *   bytes_v4_in : bytes_v4_out : bytes_v6_in : bytes_v6_out :
  *   bytes_v4_in : bytes_v4_out : bytes_v6_in : bytes_v6_out :
  *   packets_v4_in_pass : * packets_v4_in_drop : packets_v4_out_pass :
  *   packets_v4_in_pass : * packets_v4_in_drop : packets_v4_out_pass :
@@ -39,7 +39,7 @@
  *   packets_v6_out_pass : * packets_v6_out_drop : states_entries :
  *   packets_v6_out_pass : * packets_v6_out_drop : states_entries :
  *   states_searches : states_inserts : * states_removals : counters_match :
  *   states_searches : states_inserts : * states_removals : counters_match :
  *   counters_badoffset : counters_fragment : * counters_short :
  *   counters_badoffset : counters_fragment : * counters_short :
- *   counters_normalize : counters_memory 
+ *   counters_normalize : counters_memory
  *
  *
  */
  */
 #include <sys/types.h>
 #include <sys/types.h>
@@ -60,36 +60,36 @@
 static int pf_dev = -1;
 static int pf_dev = -1;
 
 
 /* Prepare if module for first use */
 /* Prepare if module for first use */
-void
+void 
 init_pf(char *s)
 init_pf(char *s)
 {
 {
     if (pf_dev == -1)
     if (pf_dev == -1)
 	if ((pf_dev = open("/dev/pf", O_RDWR)) == -1)
 	if ((pf_dev = open("/dev/pf", O_RDWR)) == -1)
-	    fatal("%s:%d: open(\"/dev/pf\") failed, %.200s", 
+	    fatal("%s:%d: open(\"/dev/pf\") failed, %.200s",
 		  __FILE__, __LINE__, strerror(errno));
 		  __FILE__, __LINE__, strerror(errno));
 
 
     info("started module pf(%s)", s);
     info("started module pf(%s)", s);
 }
 }
 /* Get pf statistics */
 /* Get pf statistics */
-int
+int 
 get_pf(char *symon_buf, int maxlen, char *arg)
 get_pf(char *symon_buf, int maxlen, char *arg)
 {
 {
     struct pf_status s;
     struct pf_status s;
     u_int64_t n;
     u_int64_t n;
-    
+
     if (pf_dev == -1) {
     if (pf_dev == -1) {
 	warning("pf(%s) failed (dev == -1)", arg);
 	warning("pf(%s) failed (dev == -1)", arg);
 	return 0;
 	return 0;
     }
     }
-    
+
     if (ioctl(pf_dev, DIOCGETSTATUS, &s)) {
     if (ioctl(pf_dev, DIOCGETSTATUS, &s)) {
 	warning("pf(%s) failed (ioctl error)", arg);
 	warning("pf(%s) failed (ioctl error)", arg);
 	return 0;
 	return 0;
     }
     }
-    
+
     if (!s.running)
     if (!s.running)
 	return 0;
 	return 0;
-    
+
     n = s.states;
     n = s.states;
     return snpack(symon_buf, maxlen, arg, MT_PF,
     return snpack(symon_buf, maxlen, arg, MT_PF,
 		  s.bcounters[0][PF_IN],
 		  s.bcounters[0][PF_IN],

+ 8 - 7
symon/symon/symon.8

@@ -55,7 +55,7 @@ should live on a different system and collect data from several
 instances in a LAN. 
 instances in a LAN. 
 .Lp
 .Lp
 .Nm
 .Nm
-priviledge needs depend on the probes used. The cpu, mem, disk and interface probes will work even when symon runs as 
+priviledge needs depend on the probes used. The cpu, mem, disk, debug and interface probes will work even when symon runs as 
 .Ar "nobody" . 
 .Ar "nobody" . 
 For pf, read and write access to 
 For pf, read and write access to 
 .Pa /dev/pf
 .Pa /dev/pf
@@ -91,22 +91,23 @@ Multiple monitor statements to different muxes are allowed. Whitespace, newlines
 .nf
 .nf
 monitor-rule = "monitor" "{" resources "}" "stream" ["to"] host [ port ]
 monitor-rule = "monitor" "{" resources "}" "stream" ["to"] host [ port ]
 resources    = resource ["(" argument ")"] [ ","|" " resources ]
 resources    = resource ["(" argument ")"] [ ","|" " resources ]
-resource     = "cpu" | "mem" | "if" | "io" | "pf"
-host         = ip4addr | hostname
-port         = [ "port" | ":" | "," ] portnumber
+resource     = "cpu" | "mem" | "if" | "io" | "pf" | "debug"
+host         = ip4addr | ip6addr | hostname
+port         = [ "port" | "," ] portnumber
 argument     = number | interfacename | diskname
 argument     = number | interfacename | diskname
 .fi
 .fi
 .Sh EXAMPLE
 .Sh EXAMPLE
 Here is an example 
 Here is an example 
 .Ar symon.conf
 .Ar symon.conf
-that monitors cpu, memory, pf, interfaces xl0/de0/lo0/wi0, disks wd[0-3]/cd[0-1]
-and streams that information to localhost on port 2100.
+that monitors cpu, memory, pf, interfaces xl0/de0/lo0/wi0, disks
+wd[0-3]/cd[0-1], debug variables debug0 to debug19 and streams that information
+to localhost on port 2100.
 .Pp
 .Pp
 .nf
 .nf
 monitor { cpu(0),  mem, pf, if(xl0), if(de0),
 monitor { cpu(0),  mem, pf, if(xl0), if(de0),
           if(lo0), if(wi0), io(wd0), io(wd1), 
           if(lo0), if(wi0), io(wd0), io(wd1), 
           io(wd2), io(wd3), io(cd0), io(cd1), 
           io(wd2), io(wd3), io(cd0), io(cd1), 
-          io(ccd0)} stream to 127.0.0.1 2100
+          io(ccd0), debug } stream to 127.0.0.1 2100
 .fi
 .fi
 .Sh SIGNALS
 .Sh SIGNALS
 .Bl -tag -width Ds
 .Bl -tag -width Ds

+ 48 - 40
symon/symon/symon.c

@@ -1,4 +1,4 @@
-/* $Id: symon.c,v 1.26 2002/10/18 12:29:48 dijkstra Exp $ */
+/* $Id: symon.c,v 1.27 2002/11/29 10:45:21 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -60,42 +60,47 @@ int flag_hup = 0;
 
 
 /* map stream types to inits and getters */
 /* map stream types to inits and getters */
 struct funcmap streamfunc[] = {
 struct funcmap streamfunc[] = {
-    {MT_IO,  init_io,  gets_io, get_io},  /* gets_io obtains entire io state, get_io = just a copy */
-    {MT_CPU, init_cpu, NULL,    get_cpu},
-    {MT_MEM, init_mem, NULL,    get_mem},
-    {MT_IF,  init_if,  NULL,    get_if},
-    {MT_PF,  init_pf,  NULL,    get_pf},
+    {MT_IO, init_io, gets_io, get_io},	/* gets_io obtains entire io state,
+					 * get_io = just a copy */
+    {MT_CPU, init_cpu, NULL, get_cpu},
+    {MT_MEM, init_mem, NULL, get_mem},
+    {MT_IF, init_if, NULL, get_if},
+    {MT_PF, init_pf, NULL, get_pf},
+    {MT_DEBUG, init_debug, NULL, get_debug},
     {MT_EOT, NULL, NULL}
     {MT_EOT, NULL, NULL}
 };
 };
 
 
 /* alarmhandler that gets called every SYMON_INTERVAL */
 /* alarmhandler that gets called every SYMON_INTERVAL */
 void 
 void 
-alarmhandler(int s) {
+alarmhandler(int s)
+{
     /* EMPTY */
     /* EMPTY */
 }
 }
-void
-exithandler(int s) {
+void 
+exithandler(int s)
+{
     info("received signal %d - quitting", s);
     info("received signal %d - quitting", s);
     exit(1);
     exit(1);
 }
 }
-void
-huphandler(int s) {
+void 
+huphandler(int s)
+{
     info("hup received");
     info("hup received");
     flag_hup = 1;
     flag_hup = 1;
 }
 }
-/* 
- * Symon is a system measurement utility. 
+/*
+ * Symon is a system measurement utility.
  *
  *
  * The main goals symon hopes to accomplish is:
  * The main goals symon hopes to accomplish is:
- * - to take fine grained measurements of system parameters 
- * - with minimal performance impact 
+ * - to take fine grained measurements of system parameters
+ * - with minimal performance impact
  * - in a secure way.
  * - in a secure way.
- * 
+ *
  * Measuring system parameters (e.g. interfaces) sometimes means traversing
  * Measuring system parameters (e.g. interfaces) sometimes means traversing
  * lists in kernel memory. Because of this the measurement of data has been
  * lists in kernel memory. Because of this the measurement of data has been
  * decoupled from the processing and storage of data. Storing the measured
  * decoupled from the processing and storage of data. Storing the measured
  * information that symon provides is done by a second program, called symux.
  * information that symon provides is done by a second program, called symux.
- * 
+ *
  * Symon can keep track of cpu, memory, disk and network interface
  * Symon can keep track of cpu, memory, disk and network interface
  * interactions. Symon was built specifically for OpenBSD.
  * interactions. Symon was built specifically for OpenBSD.
  */
  */
@@ -131,7 +136,7 @@ main(int argc, char *argv[])
 		/* cfg path needs to be absolute, we will be a daemon soon */
 		/* cfg path needs to be absolute, we will be a daemon soon */
 		if ((cfgpath = getwd(NULL)) == NULL)
 		if ((cfgpath = getwd(NULL)) == NULL)
 		    fatal("could not get working directory");
 		    fatal("could not get working directory");
-		
+
 		maxstringlen = strlen(cfgpath) + strlen(optarg) + 1;
 		maxstringlen = strlen(cfgpath) + strlen(optarg) + 1;
 		cfgfile = xmalloc(maxstringlen);
 		cfgfile = xmalloc(maxstringlen);
 		strncpy(cfgfile, cfgpath, maxstringlen);
 		strncpy(cfgfile, cfgpath, maxstringlen);
@@ -142,7 +147,8 @@ main(int argc, char *argv[])
 		cfgfile[maxstringlen] = '\0';
 		cfgfile[maxstringlen] = '\0';
 
 
 		free(cfgpath);
 		free(cfgpath);
-	    } else 
+	    }
+	    else
 		cfgfile = xstrdup(optarg);
 		cfgfile = xstrdup(optarg);
 
 
 	    break;
 	    break;
@@ -162,9 +168,9 @@ main(int argc, char *argv[])
     setgid(getgid());
     setgid(getgid());
 
 
     if (flag_debug != 1) {
     if (flag_debug != 1) {
-	if (daemon(0,0) != 0)
+	if (daemon(0, 0) != 0)
 	    fatal("daemonize failed");
 	    fatal("daemonize failed");
-	
+
 	flag_daemon = 1;
 	flag_daemon = 1;
 
 
 	/* record pid */
 	/* record pid */
@@ -173,7 +179,7 @@ main(int argc, char *argv[])
 	    fprintf(f, "%u\n", (u_int) getpid());
 	    fprintf(f, "%u\n", (u_int) getpid());
 	    fclose(f);
 	    fclose(f);
 	}
 	}
-    } 
+    }
 
 
     info("symon version %s", SYMON_VERSION);
     info("symon version %s", SYMON_VERSION);
 
 
@@ -183,9 +189,9 @@ main(int argc, char *argv[])
     /* setup signal handlers */
     /* setup signal handlers */
     signal(SIGALRM, alarmhandler);
     signal(SIGALRM, alarmhandler);
     signal(SIGHUP, huphandler);
     signal(SIGHUP, huphandler);
-    signal(SIGINT, exithandler); 
-    signal(SIGQUIT, exithandler); 
-    signal(SIGTERM, exithandler); 
+    signal(SIGINT, exithandler);
+    signal(SIGQUIT, exithandler);
+    signal(SIGTERM, exithandler);
 
 
     /* prepare crc32 */
     /* prepare crc32 */
     init_crc32();
     init_crc32();
@@ -194,22 +200,22 @@ main(int argc, char *argv[])
     SLIST_FOREACH(mux, &mul, muxes) {
     SLIST_FOREACH(mux, &mul, muxes) {
 	connect2mux(mux);
 	connect2mux(mux);
 	SLIST_FOREACH(stream, &mux->sl, streams) {
 	SLIST_FOREACH(stream, &mux->sl, streams) {
-	    (streamfunc[stream->type].init)(stream->args);
+	    (streamfunc[stream->type].init) (stream->args);
 	}
 	}
     }
     }
 
 
     /* setup alarm */
     /* setup alarm */
     timerclear(&alarminterval.it_interval);
     timerclear(&alarminterval.it_interval);
     timerclear(&alarminterval.it_value);
     timerclear(&alarminterval.it_value);
-    alarminterval.it_interval.tv_sec=
-	alarminterval.it_value.tv_sec=SYMON_INTERVAL;
+    alarminterval.it_interval.tv_sec =
+	alarminterval.it_value.tv_sec = SYMON_INTERVAL;
 
 
     if (setitimer(ITIMER_REAL, &alarminterval, NULL) != 0) {
     if (setitimer(ITIMER_REAL, &alarminterval, NULL) != 0) {
 	fatal("alarm setup failed -- %s", strerror(errno));
 	fatal("alarm setup failed -- %s", strerror(errno));
     }
     }
 
 
-    for (;;) {  /* FOREVER */
-	sleep(SYMON_INTERVAL*2);    /* alarm will always interrupt sleep */
+    for (;;) {			/* FOREVER */
+	sleep(SYMON_INTERVAL * 2);	/* alarm will always interrupt sleep */
 
 
 	if (flag_hup == 1) {
 	if (flag_hup == 1) {
 	    flag_hup = 0;
 	    flag_hup = 0;
@@ -219,7 +225,8 @@ main(int argc, char *argv[])
 	    if (!read_config_file(&newmul, cfgfile)) {
 	    if (!read_config_file(&newmul, cfgfile)) {
 		info("new configuration contains errors; keeping old configuration");
 		info("new configuration contains errors; keeping old configuration");
 		free_muxlist(&newmul);
 		free_muxlist(&newmul);
-	    } else {
+	    }
+	    else {
 		free_muxlist(&mul);
 		free_muxlist(&mul);
 		mul = newmul;
 		mul = newmul;
 		info("read configuration file '%.100s' succesfully", cfgfile);
 		info("read configuration file '%.100s' succesfully", cfgfile);
@@ -228,25 +235,26 @@ main(int argc, char *argv[])
 		SLIST_FOREACH(mux, &mul, muxes) {
 		SLIST_FOREACH(mux, &mul, muxes) {
 		    connect2mux(mux);
 		    connect2mux(mux);
 		    SLIST_FOREACH(stream, &mux->sl, streams) {
 		    SLIST_FOREACH(stream, &mux->sl, streams) {
-			(streamfunc[stream->type].init)(stream->args);
+			(streamfunc[stream->type].init) (stream->args);
 		    }
 		    }
 		}
 		}
 	    }
 	    }
-	} else {
-	    
+	}
+	else {
+
 	    /* populate for modules that get all their measurements in one go */
 	    /* populate for modules that get all their measurements in one go */
-	    for (i=0; i<MT_EOT; i++)
+	    for (i = 0; i < MT_EOT; i++)
 		if (streamfunc[i].gets != NULL)
 		if (streamfunc[i].gets != NULL)
-		    (streamfunc[i].gets)();
-	    
+		    (streamfunc[i].gets) ();
+
 	    SLIST_FOREACH(mux, &mul, muxes) {
 	    SLIST_FOREACH(mux, &mul, muxes) {
 		prepare_packet(mux);
 		prepare_packet(mux);
-		
+
 		SLIST_FOREACH(stream, &mux->sl, streams)
 		SLIST_FOREACH(stream, &mux->sl, streams)
 		    stream_in_packet(stream, mux);
 		    stream_in_packet(stream, mux);
-		
+
 		finish_packet(mux);
 		finish_packet(mux);
-		
+
 		send_packet(mux);
 		send_packet(mux);
 	    }
 	    }
 	}
 	}

+ 19 - 16
symon/symon/symon.h

@@ -1,4 +1,4 @@
-/* $Id: symon.h,v 1.21 2002/10/18 12:29:48 dijkstra Exp $ */
+/* $Id: symon.h,v 1.22 2002/11/29 10:45:21 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -40,17 +40,16 @@
 #include "conf.h"
 #include "conf.h"
 
 
 #define SYMON_PID_FILE    "/var/run/symon.pid"
 #define SYMON_PID_FILE    "/var/run/symon.pid"
-#define SYMON_INTERVAL 5                           /* measurement interval */
-#define SYMON_WARN_SENDERR 50                      /* warn every x errors */
-#define SYMON_MAX_DOBJECTS  100                    /* max dynamic alloction
-                                                     = 100 objects */
-#define SYMON_MAX_OBJSIZE  (_POSIX2_LINE_MAX)      /* max allocation unit 
-						     = _POSIX2_LINE_MAX */
+#define SYMON_INTERVAL 5	/* measurement interval */
+#define SYMON_WARN_SENDERR 50	/* warn every x errors */
+#define SYMON_MAX_DOBJECTS  100	/* max dynamic alloction = 100 objects */
+#define SYMON_MAX_OBJSIZE  (_POSIX2_LINE_MAX)	/* max allocation unit =
+						 * _POSIX2_LINE_MAX */
 struct funcmap {
 struct funcmap {
     int type;
     int type;
-    void (*init)(char *);
-    void (*gets)();
-    int (*get)(char*, int, char *);
+    void (*init) (char *);
+    void (*gets) ();
+    int (*get) (char *, int, char *);
 };
 };
 extern struct funcmap streamfunc[];
 extern struct funcmap streamfunc[];
 
 
@@ -58,24 +57,28 @@ extern struct funcmap streamfunc[];
 __BEGIN_DECLS
 __BEGIN_DECLS
 /* cpu.c */
 /* cpu.c */
 extern void init_cpu(char *);
 extern void init_cpu(char *);
-extern int  get_cpu(char *, int, char *);
+extern int get_cpu(char *, int, char *);
 
 
 /* mem.c */
 /* mem.c */
 extern void init_mem(char *);
 extern void init_mem(char *);
-extern int  get_mem(char *, int, char *);
+extern int get_mem(char *, int, char *);
 
 
 /* if.c */
 /* if.c */
 extern void init_if(char *);
 extern void init_if(char *);
-extern int  get_if(char *, int, char *);
+extern int get_if(char *, int, char *);
 
 
 /* io.c */
 /* io.c */
 extern void init_io(char *);
 extern void init_io(char *);
 extern void gets_io();
 extern void gets_io();
-extern int  get_io(char *, int, char *);
+extern int get_io(char *, int, char *);
 
 
 /* pf.c */
 /* pf.c */
 extern void init_pf(char *);
 extern void init_pf(char *);
-extern int  get_pf(char *, int, char *);
+extern int get_pf(char *, int, char *);
+
+/* debug.c */
+extern void init_debug(char *);
+extern int get_debug(char *, int, char *);
 __END_DECLS
 __END_DECLS
 
 
-#endif /*_SYMON_SYMON_H*/
+#endif				/* _SYMON_SYMON_H */

+ 38 - 41
symon/symon/symonnet.c

@@ -1,4 +1,4 @@
-/* $Id: symonnet.c,v 1.10 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: symonnet.c,v 1.11 2002/11/29 10:45:21 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -33,7 +33,7 @@
 #include <sys/types.h>
 #include <sys/types.h>
 #include <sys/socket.h>
 #include <sys/socket.h>
 
 
-#include <netinet/in.h>
+#include <netdb.h>
 
 
 #include <string.h>
 #include <string.h>
 #include <errno.h>
 #include <errno.h>
@@ -46,49 +46,46 @@
 
 
 /* Fill a mux structure with inet details */
 /* Fill a mux structure with inet details */
 void 
 void 
-connect2mux(struct mux *mux)
+connect2mux(struct mux * mux)
 {
 {
-    struct sockaddr_in sockaddr;
+    struct sockaddr_storage sockaddr;
+    int family;
 
 
-    if ((mux->symonsocket = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
-	fatal("could not obtain socket: %.200s", strerror(errno));
+    bzero((void *) &sockaddr, sizeof(sockaddr));
 
 
-    sockaddr.sin_family = AF_INET;
-    sockaddr.sin_port = 0;
-    sockaddr.sin_addr.s_addr = htonl(INADDR_ANY);
-    bzero(&sockaddr.sin_zero, 8);
+    get_mux_sockaddr(mux, SOCK_DGRAM);
+    family = mux->sockaddr.ss_family;
 
 
-    if (bind(mux->symonsocket, (struct sockaddr *) &sockaddr, 
-	     sizeof(struct sockaddr)) == -1)
-	fatal("could not bind socket: %.200s", strerror(errno));
+    get_inaddrany_sockaddr(&sockaddr, family, SOCK_DGRAM, "0");
 
 
-    mux->sockaddr.sin_family = AF_INET;
-    mux->sockaddr.sin_port = htons(mux->port);
-    mux->sockaddr.sin_addr.s_addr = htonl(mux->ip);
-    bzero(&mux->sockaddr.sin_zero, 8);
+    if ((mux->symuxsocket = socket(family, SOCK_DGRAM, 0)) == -1)
+	fatal("could not obtain socket: %.200s", strerror(errno));
+
+    if (bind(mux->symuxsocket, (struct sockaddr *) & sockaddr, sockaddr.ss_len) == -1)
+	fatal("could not bind socket: %.200s", strerror(errno));
 
 
-    info("sending packets to udp:%s:%d", 
-	 mux->name, mux->port);
+    info("sending packets to udp %s", mux->name);
 }
 }
 /* Send data stored in the mux structure to a mux */
 /* Send data stored in the mux structure to a mux */
 void 
 void 
-send_packet(struct mux *mux)
-{   
-    if (sendto(mux->symonsocket, (void *)&mux->packet.data, 
-	       mux->offset, 0, (struct sockaddr *)&mux->sockaddr, 
-	       sizeof(mux->sockaddr))
+send_packet(struct mux * mux)
+{
+    if (sendto(mux->symuxsocket, (void *) &mux->packet.data,
+	       mux->offset, 0, (struct sockaddr *) & mux->sockaddr,
+	       mux->sockaddr.ss_len)
 	!= mux->offset) {
 	!= mux->offset) {
 	mux->senderr++;
 	mux->senderr++;
     }
     }
 
 
-    if (mux->senderr >= SYMON_WARN_SENDERR)
-	warning("%d updates to mux(%u.%u.%u.%u) lost due to send errors",
-		mux->senderr, 
-		IPAS4BYTES(mux->ip)), mux->senderr = 0;
+    if (mux->senderr >= SYMON_WARN_SENDERR) {
+	warning("%d updates to mux(%s) lost due to send errors",
+		mux->senderr, mux->name);
+	mux->senderr = 0;
+    }
 }
 }
 /* Prepare a packet for data */
 /* Prepare a packet for data */
 void 
 void 
-prepare_packet(struct mux *mux) 
+prepare_packet(struct mux * mux)
 {
 {
     time_t t = time(NULL);
     time_t t = time(NULL);
 
 
@@ -97,31 +94,31 @@ prepare_packet(struct mux *mux)
     mux->packet.header.timestamp = t;
     mux->packet.header.timestamp = t;
 
 
     /* symonpacketheader is always first stream */
     /* symonpacketheader is always first stream */
-    mux->offset = 
-	setheader((char *)&mux->packet.data, 
+    mux->offset =
+	setheader((char *) &mux->packet.data,
 		  &mux->packet.header);
 		  &mux->packet.header);
 }
 }
 /* Put a stream into the packet for a mux */
 /* Put a stream into the packet for a mux */
 void 
 void 
-stream_in_packet(struct stream *stream, struct mux *mux) 
+stream_in_packet(struct stream * stream, struct mux * mux)
 {
 {
-    mux->offset += 
-	(streamfunc[stream->type].get)      /* call getter of stream */
-	(&mux->packet.data[mux->offset],    /* packet buffer */
-	 sizeof(mux->packet.data) - mux->offset,    /* maxlen */
-	 stream->args);
+    mux->offset +=
+    (streamfunc[stream->type].get)	/* call getter of stream */
+    (&mux->packet.data[mux->offset],	/* packet buffer */
+     sizeof(mux->packet.data) - mux->offset,	/* maxlen */
+     stream->args);
 }
 }
 /* Ready a packet for transmission, set length and crc */
 /* Ready a packet for transmission, set length and crc */
-void finish_packet(struct mux *mux) 
+void 
+finish_packet(struct mux * mux)
 {
 {
     mux->packet.header.length = mux->offset;
     mux->packet.header.length = mux->offset;
     mux->packet.header.crc = 0;
     mux->packet.header.crc = 0;
 
 
     /* fill in correct header with crc = 0 */
     /* fill in correct header with crc = 0 */
-    setheader((char *)&mux->packet.data, &mux->packet.header);
+    setheader((char *) &mux->packet.data, &mux->packet.header);
 
 
     /* fill in correct header with crc */
     /* fill in correct header with crc */
     mux->packet.header.crc = crc32(&mux->packet.data, mux->offset);
     mux->packet.header.crc = crc32(&mux->packet.data, mux->offset);
-    setheader((char *)&mux->packet.data, &mux->packet.header);
+    setheader((char *) &mux->packet.data, &mux->packet.header);
 }
 }
-

+ 2 - 2
symon/symon/symonnet.h

@@ -1,4 +1,4 @@
-/* $Id: symonnet.h,v 1.4 2002/09/14 15:49:39 dijkstra Exp $ */
+/* $Id: symonnet.h,v 1.5 2002/11/29 10:45:21 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -43,4 +43,4 @@ void prepare_packet(struct mux *);
 void stream_in_packet(struct stream *, struct mux *);
 void stream_in_packet(struct stream *, struct mux *);
 void finish_packet(struct mux *);
 void finish_packet(struct mux *);
 __END_DECLS
 __END_DECLS
-#endif /* _SYMON_SYMONNET_H */
+#endif				/* _SYMON_SYMONNET_H */

+ 1 - 0
symon/symon2web/Makefile

@@ -23,4 +23,5 @@ install:
 	${INSTALL} -c -m 444 -g www -o www symon.css		${PREFIX}/${WEBDIR}
 	${INSTALL} -c -m 444 -g www -o www symon.css		${PREFIX}/${WEBDIR}
 	${INSTALL} -c -m 444 -g www -o www symon.png		${PREFIX}/${WEBDIR}
 	${INSTALL} -c -m 444 -g www -o www symon.png		${PREFIX}/${WEBDIR}
 	${INSTALL} -c -m 444 -g www -o www spacer.png		${PREFIX}/${WEBDIR}
 	${INSTALL} -c -m 444 -g www -o www spacer.png		${PREFIX}/${WEBDIR}
+	${INSTALL} -c -m 444 -g www -o www test_config.php	${PREFIX}/${WEBDIR
 
 

+ 1 - 0
symon/symon2web/class_cpu.inc

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: class_cpu.inc,v 1.4 2002/11/29 10:45:46 dijkstra Exp $
 require_once("class_graph.inc");
 require_once("class_graph.inc");
 
 
 class CPU_Graph extends Graph {
 class CPU_Graph extends Graph {

+ 1 - 2
symon/symon2web/class_graph.inc

@@ -1,9 +1,8 @@
 <?php
 <?php
-// $Id: class_graph.inc,v 1.6 2002/10/18 12:30:20 dijkstra Exp $
+// $Id: class_graph.inc,v 1.7 2002/11/29 10:45:46 dijkstra Exp $
 //
 //
 // Base class for all graph classes. 
 // Base class for all graph classes. 
 
 
-// 
 class Graph {
 class Graph {
     var $debug;
     var $debug;
     var $graphdefaults;
     var $graphdefaults;

+ 1 - 0
symon/symon2web/class_if.inc

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: class_if.inc,v 1.9 2002/11/29 10:45:46 dijkstra Exp $
 require_once("class_graph.inc");
 require_once("class_graph.inc");
 
 
 class IF_Graph extends Graph {
 class IF_Graph extends Graph {

+ 1 - 0
symon/symon2web/class_io.inc

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: class_io.inc,v 1.4 2002/11/29 10:45:46 dijkstra Exp $
 require_once("class_graph.inc");
 require_once("class_graph.inc");
 
 
 class IO_Graph extends Graph {
 class IO_Graph extends Graph {

+ 1 - 0
symon/symon2web/class_mem.inc

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: class_mem.inc,v 1.4 2002/11/29 10:45:46 dijkstra Exp $
 require_once("class_graph.inc");
 require_once("class_graph.inc");
 
 
 class MEM_Graph extends Graph {
 class MEM_Graph extends Graph {

+ 1 - 0
symon/symon2web/class_pf.inc

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: class_pf.inc,v 1.4 2002/11/29 10:45:46 dijkstra Exp $
 require_once("class_graph.inc");
 require_once("class_graph.inc");
 
 
 class PF_Graph extends Graph {
 class PF_Graph extends Graph {

+ 1 - 0
symon/symon2web/graph_cpu.php

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: graph_cpu.php,v 1.8 2002/11/29 10:45:46 dijkstra Exp $
 require_once("datasources.inc");
 require_once("datasources.inc");
 require_once("class_cpu.inc");
 require_once("class_cpu.inc");
 $g = new CPU_Graph();
 $g = new CPU_Graph();

+ 1 - 0
symon/symon2web/graph_if.php

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: graph_if.php,v 1.9 2002/11/29 10:45:46 dijkstra Exp $
 require_once("datasources.inc");
 require_once("datasources.inc");
 require_once("class_if.inc");
 require_once("class_if.inc");
 $g = new IF_Graph();
 $g = new IF_Graph();

+ 1 - 0
symon/symon2web/graph_io.php

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: graph_io.php,v 1.5 2002/11/29 10:45:46 dijkstra Exp $
 require_once("datasources.inc");
 require_once("datasources.inc");
 require_once("class_io.inc");
 require_once("class_io.inc");
 $g = new IO_Graph();
 $g = new IO_Graph();

+ 1 - 0
symon/symon2web/graph_mem.php

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: graph_mem.php,v 1.8 2002/11/29 10:45:46 dijkstra Exp $
 require_once("datasources.inc");
 require_once("datasources.inc");
 require_once("class_mem.inc");
 require_once("class_mem.inc");
 $g = new MEM_Graph();
 $g = new MEM_Graph();

+ 1 - 0
symon/symon2web/graph_pf.php

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: graph_pf.php,v 1.3 2002/11/29 10:45:46 dijkstra Exp $
 require_once("datasources.inc");
 require_once("datasources.inc");
 require_once("class_pf.inc");
 require_once("class_pf.inc");
 $g = new PF_Graph();
 $g = new PF_Graph();

+ 2 - 0
symon/symon2web/index.php

@@ -1,4 +1,5 @@
 <?php
 <?php
+// $Id: index.php,v 1.14 2002/11/29 10:45:46 dijkstra Exp $
 require_once('datasources.inc');
 require_once('datasources.inc');
 require_once('class_cpu.inc');
 require_once('class_cpu.inc');
 require_once('class_if.inc');
 require_once('class_if.inc');
@@ -9,6 +10,7 @@ require_once('class_pf.inc');
 if (!empty($HTTP_SERVER_VARS["QUERY_STRING"])) {
 if (!empty($HTTP_SERVER_VARS["QUERY_STRING"])) {
     $args = $HTTP_SERVER_VARS["QUERY_STRING"];
     $args = $HTTP_SERVER_VARS["QUERY_STRING"];
     // rework args to contain ony last set 'command' 
     // rework args to contain ony last set 'command' 
+    $selected_machine = "";
     $options = array();
     $options = array();
     $allargs = explode('&', $args);
     $allargs = explode('&', $args);
     $i = 0;
     $i = 0;

+ 78 - 0
symon/symon2web/test_config.php

@@ -0,0 +1,78 @@
+<html>
+ <head>
+  <title>Symon2Web configuration test</title>
+ </head>
+ <body>
+<?php
+// $Id: test_config.php,v 1.1 2002/11/29 10:45:46 dijkstra Exp $
+//
+// Test configuration variables
+require_once('datasources.inc');
+require_once('class_cpu.inc');
+require_once('class_if.inc');
+require_once('class_io.inc');
+require_once('class_mem.inc');
+require_once('class_pf.inc');
+
+// Test to see if we can find rrdtool
+// Test to see if we can run rrdtool
+print "Trying to find rrdtool:<b>";
+$g = new CPU_Graph();
+$g->init(); $g->parseoptions();
+$rrdtool = substr($g->get("rrdtool"), 0, strpos($g->get("rrdtool"), " "));
+print $rrdtool;
+if (!is_string($rrdtool)) {
+    exit("Internal error, class_graph does not set a default rrdtool location!");
+} else {
+    if (!is_file($rrdtool)) {
+	exit("'$rrdtool' does not point to a file");
+    }
+
+    if (!is_executable($rrdtool)) {
+	exit("'$rrdtool' is not executable");
+    }
+}
+print "</b><br>rrdtool -v outputs:<hr><pre>";
+passthru($rrdtool.' -v');
+print "</pre><hr>";
+// Test to see if we can find rrd files
+print "Trying to find symon rrd files:<br>";
+$root_dir = dir($symon2web["tree"]);
+while ($machine = $root_dir->read()) {
+    if ($machine != '.' && 
+	$machine != '..' && 
+	is_dir($symon2web["tree"]."/".$machine)) {
+	$symon2web["machine"][$machine] = $symon2web["tree"]."/".$machine;
+    }
+}
+reset($symon2web["machine"]);
+while (list($machine, $dir) = each($symon2web["machine"])) {
+    $readable = TRUE;
+    print '<b>machine('.$machine.')=</b><br>';
+    $machine_dir = dir($dir);
+    while ($filename = $machine_dir->read()) {
+	$file = $dir."/".$filename;
+	if (is_file($file) && 
+	    preg_match("/^(cpu|if|io|mem|pf)(_([a-z]+))?([0-9]?).rrd$/", 
+		       $filename, $match)) {
+	    print "&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;$file";
+	    if (!is_readable($file)) {
+		$readable = FALSE;
+		print "!";
+	    }
+	    print "<br>";
+	}
+    }
+    print "}<br>";
+    if ($readable == FALSE) {
+	print "Note that files tagged with an exclamation mark could not be read.<br><br>";
+    } else {
+	print "And all files accessable.<br><br>";
+    }
+}
+// Test to see if we can load rrd files
+// Tie it all together
+?>
+</body>
+</html>
+

+ 0 - 4
symon/symux/.gdbinit

@@ -1,4 +0,0 @@
-file symux
-set args -d -f t
-b readconf.c:217
-r

+ 21 - 4
symon/symux/c_smrrds.sh

@@ -1,5 +1,5 @@
 #!/bin/sh
 #!/bin/sh
-# $Id: c_smrrds.sh,v 1.13 2002/10/25 15:24:55 dijkstra Exp $
+# $Id: c_smrrds.sh,v 1.14 2002/11/29 10:49:20 dijkstra Exp $
 
 
 #
 #
 # Copyright (c) 2001-2002 Willem Dijkstra
 # Copyright (c) 2001-2002 Willem Dijkstra
@@ -91,8 +91,8 @@ if [ `echo $i | egrep -e "^($INTERFACES)$"` ]; then i=if_$i.rrd; fi
 if [ `echo $i | egrep -e "^($VIRTUALINTERFACES)$"` ]; then i=if_$i.rrd; fi
 if [ `echo $i | egrep -e "^($VIRTUALINTERFACES)$"` ]; then i=if_$i.rrd; fi
 # add io_*.rrd if it is a disk
 # add io_*.rrd if it is a disk
 if [ `echo $i | egrep -e "^($DISKS)$"` ]; then i=io_$i.rrd; fi
 if [ `echo $i | egrep -e "^($DISKS)$"` ]; then i=io_$i.rrd; fi
-# add .rrd if it is a cpu, mem, or pf
-if [ `echo $i | egrep -e "^(cpu[0-9]|mem|pf)$"` ]; then i=$i.rrd; fi
+# add .rrd if it is a cpu, etc.
+if [ `echo $i | egrep -e "^(cpu[0-9]|mem|pf|debug)$"` ]; then i=$i.rrd; fi
 
 
 if [ -f $i ]; then
 if [ -f $i ]; then
     echo "$i exists - ignoring"
     echo "$i exists - ignoring"
@@ -155,6 +155,23 @@ if_*.rrd)
     echo "$i created"
     echo "$i created"
     ;;
     ;;
 
 
+debug.rrd)
+    # Build debug file
+    rrdtool create $i $RRD_ARGS \
+	DS:debug0:COUNTER:5:U:U DS:debug1:COUNTER:5:U:U \
+	DS:debug2:COUNTER:5:U:U DS:debug3:COUNTER:5:U:U \
+	DS:debug4:COUNTER:5:U:U DS:debug5:COUNTER:5:U:U \
+	DS:debug6:COUNTER:5:U:U DS:debug7:COUNTER:5:U:U \
+	DS:debug8:COUNTER:5:U:U DS:debug9:COUNTER:5:U:U \
+	DS:debug10:COUNTER:5:U:U DS:debug11:COUNTER:5:U:U \
+	DS:debug12:COUNTER:5:U:U DS:debug13:COUNTER:5:U:U \
+	DS:debug14:COUNTER:5:U:U DS:debug15:COUNTER:5:U:U \
+	DS:debug16:COUNTER:5:U:U DS:debug17:COUNTER:5:U:U \
+	DS:debug18:COUNTER:5:U:U DS:debug19:COUNTER:5:U:U \
+	$RRA_SETUP
+    echo "$i created"
+    ;;
+    
 pf.rrd)
 pf.rrd)
     # Build pf file
     # Build pf file
     rrdtool create $i $RRD_ARGS \
     rrdtool create $i $RRD_ARGS \
@@ -195,7 +212,7 @@ io_*.rrd)
     # Default match
     # Default match
     cat <<EOF
     cat <<EOF
 Usage: $0 all
 Usage: $0 all
-       $0 cpu0|mem|pf|<if>|<io>
+       $0 cpu0|mem|pf|debug|<if>|<io>
 
 
 Where:
 Where:
 if=	`echo $INTERFACES|
 if=	`echo $INTERFACES|

+ 138 - 109
symon/symux/readconf.c

@@ -1,4 +1,4 @@
-/* $Id: readconf.c,v 1.15 2002/10/25 15:25:07 dijkstra Exp $ */
+/* $Id: readconf.c,v 1.16 2002/11/29 10:49:35 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -32,37 +32,35 @@
 
 
 #include <sys/queue.h>
 #include <sys/queue.h>
 #include <sys/stat.h>
 #include <sys/stat.h>
-#include <sys/types.h>
 
 
-#include <stdarg.h>
-#include <stdio.h>
 #include <string.h>
 #include <string.h>
-#include <assert.h>
-#include <limits.h>
 #include <fcntl.h>
 #include <fcntl.h>
 #include <unistd.h>
 #include <unistd.h>
 
 
-#include "xmalloc.h"
-#include "lex.h"
+#include "data.h"
 #include "error.h"
 #include "error.h"
+#include "lex.h"
 #include "net.h"
 #include "net.h"
-#include "data.h"
+#include "readconf.h"
+#include "xmalloc.h"
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
-int read_mux(struct muxlist *mul, struct lex *);
-int read_source(struct sourcelist *sol, struct lex *);
+int read_mux(struct muxlist * mul, struct lex *);
+int read_source(struct sourcelist * sol, struct lex *);
 int insert_filename(char *, int, int, char *);
 int insert_filename(char *, int, int, char *);
 __END_DECLS
 __END_DECLS
 
 
+const char *default_symux_port = SYMUX_PORT;
+
 int 
 int 
-insert_filename(char *path, int maxlen, int type, char *args) 
+insert_filename(char *path, int maxlen, int type, char *args)
 {
 {
     char *ts;
     char *ts;
     char *ta;
     char *ta;
 
 
     ts = ta = NULL;
     ts = ta = NULL;
 
 
-    switch(type) {
+    switch (type) {
     case MT_CPU:
     case MT_CPU:
 	ts = "cpu";
 	ts = "cpu";
 	ta = args;
 	ta = args;
@@ -83,63 +81,70 @@ insert_filename(char *path, int maxlen, int type, char *args)
 	ts = "pf";
 	ts = "pf";
 	ta = "";
 	ta = "";
 	break;
 	break;
+    case MT_DEBUG:
+	ts = "debug";
+	ta = "";
+	break;
     default:
     default:
 	warning("%s:%d: internal error: type (%d) unknown",
 	warning("%s:%d: internal error: type (%d) unknown",
 		__FILE__, __LINE__, type);
 		__FILE__, __LINE__, type);
 	return 0;
 	return 0;
     }
     }
-    
-    if ((snprintf(path, maxlen, "/%s%s.rrd", ts, ta)) >= maxlen) 
+
+    if ((snprintf(path, maxlen, "/%s%s.rrd", ts, ta)) >= maxlen)
 	return 0;
 	return 0;
     else
     else
 	return 1;
 	return 1;
 }
 }
-/* mux <host> (port|:|,| ) <number> */
+/* mux <host> (port|,| ) <number> */
 int 
 int 
-read_mux(struct muxlist *mul, struct lex *l)
+read_mux(struct muxlist * mul, struct lex * l)
 {
 {
-    struct mux *m;
+    char muxname[_POSIX2_LINE_MAX];
+    struct mux *mux;
 
 
-    if (! SLIST_EMPTY(mul)) {
-	warning("%s:%d: only one mux statement allowed", 
+    if (!SLIST_EMPTY(mul)) {
+	warning("%s:%d: only one mux statement allowed",
 		l->filename, l->cline);
 		l->filename, l->cline);
 	return 0;
 	return 0;
     }
     }
-    
+
     lex_nexttoken(l);
     lex_nexttoken(l);
-    if (!lookup(l->token)) {
+    if (!getip(l->token)) {
 	warning("%s:%d: could not resolve '%s'",
 	warning("%s:%d: could not resolve '%s'",
-		l->filename, l->cline, l->token );
+		l->filename, l->cline, l->token);
 	return 0;
 	return 0;
     }
     }
 
 
-    m = add_mux(mul, lookup_address);
-    m->ip = lookup_ip;
+    mux = add_mux(mul, SYMON_UNKMUX);
+    mux->addr = xstrdup((const char *) &res_host);
 
 
     /* check for port statement */
     /* check for port statement */
     lex_nexttoken(l);
     lex_nexttoken(l);
-    if (l->op == LXT_PORT || l->op == LXT_COLON || l->op == LXT_COMMA)
+
+    if (l->op == LXT_PORT || l->op == LXT_COMMA)
 	lex_nexttoken(l);
 	lex_nexttoken(l);
-    else {
-	if (l->type != LXY_NUMBER) {
-	    lex_ungettoken(l);
-	    m->port = SYMUX_PORT;
-	    return 1;
-	}
-    }
 
 
     if (l->type != LXY_NUMBER) {
     if (l->type != LXY_NUMBER) {
-	parse_error(l, "<number>");
-	return 0;
+	lex_ungettoken(l);
+	mux->port = xstrdup(default_symux_port);
     }
     }
+    else {
+	mux->port = xstrdup((const char *) l->token);
+    }
+
+    bzero(&muxname, sizeof(muxname));
+    snprintf(&muxname[0], sizeof(muxname), "%s %s", mux->addr, mux->port);
+
+    if (rename_mux(mul, mux, muxname) == NULL)
+	fatal("%s:%d: internal error: dual mux", __FILE__, __LINE__);
 
 
-    m->port = l->value;
 
 
     return 1;
     return 1;
 }
 }
 /* source <host> { accept ... | write ... | datadir ... } */
 /* source <host> { accept ... | write ... | datadir ... } */
 int 
 int 
-read_source(struct sourcelist *sol, struct lex *l)
+read_source(struct sourcelist * sol, struct lex * l)
 {
 {
     struct source *source;
     struct source *source;
     struct stream *stream;
     struct stream *stream;
@@ -153,15 +158,14 @@ read_source(struct sourcelist *sol, struct lex *l)
 
 
     /* get hostname */
     /* get hostname */
     lex_nexttoken(l);
     lex_nexttoken(l);
-    if (!lookup(l->token)) {
+    if (!getip(l->token)) {
 	warning("%s:%d: could not resolve '%s'",
 	warning("%s:%d: could not resolve '%s'",
-		l->filename, l->cline, l->token );
-	return 0; 
+		l->filename, l->cline, l->token);
+	return 0;
     }
     }
 
 
-    source = add_source(sol, lookup_address);
-    source->ip = lookup_ip;
-    
+    source = add_source(sol, res_host);
+
     EXPECT(l, LXT_BEGIN);
     EXPECT(l, LXT_BEGIN);
     while (lex_nexttoken(l)) {
     while (lex_nexttoken(l)) {
 	switch (l->op) {
 	switch (l->op) {
@@ -175,6 +179,7 @@ read_source(struct sourcelist *sol, struct lex *l)
 		case LXT_IO:
 		case LXT_IO:
 		case LXT_MEM:
 		case LXT_MEM:
 		case LXT_PF:
 		case LXT_PF:
+		case LXT_DEBUG:
 		    st = token2type(l->op);
 		    st = token2type(l->op);
 		    strncpy(&sn[0], l->token, _POSIX2_LINE_MAX);
 		    strncpy(&sn[0], l->token, _POSIX2_LINE_MAX);
 
 
@@ -194,28 +199,29 @@ read_source(struct sourcelist *sol, struct lex *l)
 			    parse_error(l, ")");
 			    parse_error(l, ")");
 			    return 0;
 			    return 0;
 			}
 			}
-		    } else {
+		    }
+		    else {
 			lex_ungettoken(l);
 			lex_ungettoken(l);
-			sa[0]='\0';
+			sa[0] = '\0';
 		    }
 		    }
 
 
 		    if ((stream = add_source_stream(source, st, sa)) == NULL) {
 		    if ((stream = add_source_stream(source, st, sa)) == NULL) {
-			warning("%s:%d: stream %s(%s) redefined", 
+			warning("%s:%d: stream %s(%s) redefined",
 				l->filename, l->cline, sn, sa);
 				l->filename, l->cline, sn, sa);
 			return 0;
 			return 0;
 		    }
 		    }
 
 
-		    break; /* LXT_CPU/LXT_IF/LXT_IO/LXT_MEM/LXT_PF */
+		    break;	/* LXT_CPU/IF/IO/MEM/PF/DEBUG */
 		case LXT_COMMA:
 		case LXT_COMMA:
 		    break;
 		    break;
 		default:
 		default:
-		    parse_error(l, "{cpu|mem|if|io|pf}");
+		    parse_error(l, "{cpu|mem|if|io|pf|debug}");
 		    return 0;
 		    return 0;
 
 
 		    break;
 		    break;
 		}
 		}
 	    }
 	    }
-	    break; /* LXT_ACCEPT */
+	    break;		/* LXT_ACCEPT */
 	    /* datadir "path" */
 	    /* datadir "path" */
 	case LXT_DATADIR:
 	case LXT_DATADIR:
 	    lex_nexttoken(l);
 	    lex_nexttoken(l);
@@ -230,62 +236,65 @@ read_source(struct sourcelist *sol, struct lex *l)
 	    bzero(&sb, sizeof(struct stat));
 	    bzero(&sb, sizeof(struct stat));
 
 
 	    if (stat(l->token, &sb) == 0) {
 	    if (stat(l->token, &sb) == 0) {
-		if (! (sb.st_mode & S_IFDIR)) {
+		if (!(sb.st_mode & S_IFDIR)) {
 		    warning("%s:%d: datadir path '%s' is not a directory",
 		    warning("%s:%d: datadir path '%s' is not a directory",
 			    l->filename, l->cline, l->token);
 			    l->filename, l->cline, l->token);
 		    return 0;
 		    return 0;
 		}
 		}
-	    } else {
+	    }
+	    else {
 		warning("%s:%d: could not stat datadir path '%s'",
 		warning("%s:%d: could not stat datadir path '%s'",
 			l->filename, l->cline, l->token);
 			l->filename, l->cline, l->token);
 		return 0;
 		return 0;
 	    }
 	    }
 
 
 	    strncpy(&path[0], l->token, _POSIX2_LINE_MAX);
 	    strncpy(&path[0], l->token, _POSIX2_LINE_MAX);
-	    path[_POSIX2_LINE_MAX-1] = '\0';
-	    
+	    path[_POSIX2_LINE_MAX - 1] = '\0';
+
 	    pc = strlen(path);
 	    pc = strlen(path);
-	    
-	    if (path[pc-1] == '/') {
-		path[pc-1] = '\0';
+
+	    if (path[pc - 1] == '/') {
+		path[pc - 1] = '\0';
 		pc--;
 		pc--;
 	    }
 	    }
-	    
+
 	    /* add path to empty streams */
 	    /* add path to empty streams */
 	    SLIST_FOREACH(stream, &source->sl, streams) {
 	    SLIST_FOREACH(stream, &source->sl, streams) {
 		if (stream->file == NULL) {
 		if (stream->file == NULL) {
-		    if (!(insert_filename(&path[pc], 
-					  _POSIX2_LINE_MAX - pc, 
-					  stream->type, 
+		    if (!(insert_filename(&path[pc],
+					  _POSIX2_LINE_MAX - pc,
+					  stream->type,
 					  stream->args))) {
 					  stream->args))) {
 			if (stream->args && strlen(stream->args)) {
 			if (stream->args && strlen(stream->args)) {
 			    warning("%s:%d: failed to construct stream "
 			    warning("%s:%d: failed to construct stream "
 				    "%s(%s) filename using datadir '%s'",
 				    "%s(%s) filename using datadir '%s'",
-				    l->filename, l->cline, 
-				    type2str(stream->type), 
+				    l->filename, l->cline,
+				    type2str(stream->type),
 				    stream->args, l->token);
 				    stream->args, l->token);
-			} else {
+			}
+			else {
 			    warning("%s:%d: failed to construct stream "
 			    warning("%s:%d: failed to construct stream "
 				    "%s) filename using datadir '%s'",
 				    "%s) filename using datadir '%s'",
-				    l->filename, l->cline, 
-				    type2str(stream->type), 
+				    l->filename, l->cline,
+				    type2str(stream->type),
 				    l->token);
 				    l->token);
 			}
 			}
 			return 0;
 			return 0;
 		    }
 		    }
-		    
+
 		    /* try filename */
 		    /* try filename */
 		    if ((fd = open(path, O_RDWR | O_NONBLOCK, 0)) == -1) {
 		    if ((fd = open(path, O_RDWR | O_NONBLOCK, 0)) == -1) {
-			warning("%s:%d: file '%s', guessed by datadir,  cannot be opened", 
+			warning("%s:%d: file '%s', guessed by datadir,  cannot be opened",
 				l->filename, l->cline, path);
 				l->filename, l->cline, path);
 			return 0;
 			return 0;
-		    } else {
+		    }
+		    else {
 			close(fd);
 			close(fd);
 			stream->file = xstrdup(path);
 			stream->file = xstrdup(path);
 		    }
 		    }
 		}
 		}
 	    }
 	    }
-	    break; /* LXT_DATADIR */
+	    break;		/* LXT_DATADIR */
 	    /* write cpu(0) in "filename" */
 	    /* write cpu(0) in "filename" */
 	case LXT_WRITE:
 	case LXT_WRITE:
 	    lex_nexttoken(l);
 	    lex_nexttoken(l);
@@ -295,9 +304,10 @@ read_source(struct sourcelist *sol, struct lex *l)
 	    case LXT_IO:
 	    case LXT_IO:
 	    case LXT_MEM:
 	    case LXT_MEM:
 	    case LXT_PF:
 	    case LXT_PF:
+	    case LXT_DEBUG:
 		st = token2type(l->op);
 		st = token2type(l->op);
 		strncpy(&sn[0], l->token, _POSIX2_LINE_MAX);
 		strncpy(&sn[0], l->token, _POSIX2_LINE_MAX);
-		
+
 		/* parse arg */
 		/* parse arg */
 		lex_nexttoken(l);
 		lex_nexttoken(l);
 		if (l->op == LXT_OPEN) {
 		if (l->op == LXT_OPEN) {
@@ -313,50 +323,54 @@ read_source(struct sourcelist *sol, struct lex *l)
 			parse_error(l, ")");
 			parse_error(l, ")");
 			return 0;
 			return 0;
 		    }
 		    }
-		} else {
+		}
+		else {
 		    lex_ungettoken(l);
 		    lex_ungettoken(l);
-		    sa[0]='\0';
+		    sa[0] = '\0';
 		}
 		}
-		
+
 		EXPECT(l, LXT_IN);
 		EXPECT(l, LXT_IN);
 
 
 		lex_nexttoken(l);
 		lex_nexttoken(l);
-		
+
 		if ((stream = find_source_stream(source, st, sa)) == NULL) {
 		if ((stream = find_source_stream(source, st, sa)) == NULL) {
 		    if (strlen(sa)) {
 		    if (strlen(sa)) {
-			warning("%s:%d: stream %s(%s) is not accepted for %s", 
-				l->filename, l->cline, sn, sa, source->name);
+			warning("%s:%d: stream %s(%s) is not accepted for %s",
+				l->filename, l->cline, sn, sa, source->addr);
 			return 0;
 			return 0;
-		    } else {
-			warning("%s:%d: stream %s is not accepted for %s", 
-				l->filename, l->cline, sn, source->name);
+		    }
+		    else {
+			warning("%s:%d: stream %s is not accepted for %s",
+				l->filename, l->cline, sn, source->addr);
 			return 0;
 			return 0;
 		    }
 		    }
-		} else {
+		}
+		else {
 		    /* try filename */
 		    /* try filename */
 		    if ((fd = open(l->token, O_RDWR | O_NONBLOCK, 0)) == -1) {
 		    if ((fd = open(l->token, O_RDWR | O_NONBLOCK, 0)) == -1) {
-			warning("%s:%d: file '%s' cannot be opened", 
+			warning("%s:%d: file '%s' cannot be opened",
 				l->filename, l->cline, l->token);
 				l->filename, l->cline, l->token);
 			return 0;
 			return 0;
-		    } else {
+		    }
+		    else {
 			close(fd);
 			close(fd);
 
 
 			if (stream->file != NULL) {
 			if (stream->file != NULL) {
 			    warning("%s:%d: file '%s' overwrites previous definition '%s'",
 			    warning("%s:%d: file '%s' overwrites previous definition '%s'",
-				    l->filename, l->cline, l->token, stream->file);
+			     l->filename, l->cline, l->token, stream->file);
 			    xfree(stream->file);
 			    xfree(stream->file);
 			}
 			}
 
 
 			stream->file = xstrdup(l->token);
 			stream->file = xstrdup(l->token);
 		    }
 		    }
 		}
 		}
-		break; /* LXT_CPU/LXT_IF/LXT_IO/LXT_MEM/LXT_PF */
+		break;		/* LXT_CPU/IF/IO/MEM/PF/DEBUG */
 	    default:
 	    default:
-		parse_error(l, "{cpu|mem|if|io}");
+		parse_error(l, "{cpu|mem|if|io|debug}");
 		return 0;
 		return 0;
 		break;
 		break;
 	    }
 	    }
-	    break; /* LXT_WRITE */
+	    break;		/* LXT_WRITE */
 	case LXT_END:
 	case LXT_END:
 	    return 1;
 	    return 1;
 	default:
 	default:
@@ -365,75 +379,90 @@ read_source(struct sourcelist *sol, struct lex *l)
 	}
 	}
     }
     }
 
 
-    warning("%s:%d: missing close brace on source statement", 
+    warning("%s:%d: missing close brace on source statement",
 	    l->filename, l->cline);
 	    l->filename, l->cline);
 
 
     return 0;
     return 0;
 }
 }
 /* Read symux.conf */
 /* Read symux.conf */
-int  
-read_config_file(struct muxlist *mul, 
-		 struct sourcelist *sol, 
-		 const char *filename)
+int 
+read_config_file(struct muxlist * mul, const char *filename)
 {
 {
     struct lex *l;
     struct lex *l;
     struct source *source;
     struct source *source;
     struct stream *stream;
     struct stream *stream;
-
+    struct mux *mux;
+    struct sourcelist sol;
     SLIST_INIT(mul);
     SLIST_INIT(mul);
-    SLIST_INIT(sol);
+    SLIST_INIT(&sol);
 
 
     if ((l = open_lex(filename)) == NULL)
     if ((l = open_lex(filename)) == NULL)
 	return 0;
 	return 0;
-    
+
     while (lex_nexttoken(l)) {
     while (lex_nexttoken(l)) {
-    /* expecting keyword now */
+	/* expecting keyword now */
 	switch (l->op) {
 	switch (l->op) {
 	case LXT_MUX:
 	case LXT_MUX:
-	    if (!read_mux(mul, l))
+	    if (!read_mux(mul, l)) {
+		free_sourcelist(&sol);
 		return 0;
 		return 0;
+	    }
 	    break;
 	    break;
 	case LXT_SOURCE:
 	case LXT_SOURCE:
-	    if (!read_source(sol, l))
+	    if (!read_source(&sol, l)) {
+		free_sourcelist(&sol);
 		return 0;
 		return 0;
+	    }
 	    break;
 	    break;
 	default:
 	default:
-	    parse_error(l, "mux|source" );
+	    parse_error(l, "mux|source");
+	    free_sourcelist(&sol);
 	    return 0;
 	    return 0;
 	    break;
 	    break;
 	}
 	}
     }
     }
-    
+
     /* sanity checks */
     /* sanity checks */
     if (SLIST_EMPTY(mul)) {
     if (SLIST_EMPTY(mul)) {
+	free_sourcelist(&sol);
 	warning("%s: no mux statement seen",
 	warning("%s: no mux statement seen",
 		l->filename);
 		l->filename);
 	return 0;
 	return 0;
     }
     }
+    else {
+	mux = SLIST_FIRST(mul);
+	mux->sol = sol;
+	if (strncmp(SYMON_UNKMUX, mux->name, sizeof(SYMON_UNKMUX)) == 0) {
+	    /* mux was not initialised for some reason */
+	    return 0;
+	}
+    }
 
 
-    if (SLIST_EMPTY(sol)) {
-	warning("%s: no source section seen", 
+    if (SLIST_EMPTY(&sol)) {
+	warning("%s: no source section seen",
 		l->filename);
 		l->filename);
 	return 0;
 	return 0;
-    } else {
-	SLIST_FOREACH(source, sol, sources) {
+    }
+    else {
+	SLIST_FOREACH(source, &sol, sources) {
 	    if (SLIST_EMPTY(&source->sl)) {
 	    if (SLIST_EMPTY(&source->sl)) {
-		warning("%s: no streams accepted for source '%s'", 
-			l->filename, source->name);
+		warning("%s: no streams accepted for source '%s'",
+			l->filename, source->addr);
 		return 0;
 		return 0;
-	    } else {
+	    }
+	    else {
 		SLIST_FOREACH(stream, &source->sl, streams) {
 		SLIST_FOREACH(stream, &source->sl, streams) {
 		    if (stream->file == NULL) {
 		    if (stream->file == NULL) {
 			warning("%s: no filename specified for stream '%s(%s)' in source '%s'",
 			warning("%s: no filename specified for stream '%s(%s)' in source '%s'",
-				l->filename, type2str(stream->type), stream->args, source->name);
+				l->filename, type2str(stream->type), stream->args, source->addr);
 			return 0;
 			return 0;
 		    }
 		    }
 		}
 		}
 	    }
 	    }
 	}
 	}
     }
     }
-    
+
     close_lex(l);
     close_lex(l);
-    
+
     return 1;
     return 1;
 }
 }

+ 3 - 5
symon/symux/readconf.h

@@ -1,4 +1,4 @@
-/* $Id: readconf.h,v 1.5 2002/09/14 15:54:55 dijkstra Exp $ */
+/* $Id: readconf.h,v 1.6 2002/11/29 10:49:35 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -37,9 +37,7 @@
 #include "data.h"
 #include "data.h"
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
-int read_config_file(struct muxlist *, struct sourcelist *, const char *);
+int read_config_file(struct muxlist *, const char *);
 __END_DECLS
 __END_DECLS
 
 
-#endif /*_SYMUX_READCONF_H*/
-
-
+#endif				/* _SYMUX_READCONF_H */

+ 142 - 96
symon/symux/share.c

@@ -1,4 +1,4 @@
-/* $Id: share.c,v 1.9 2002/09/14 15:54:55 dijkstra Exp $ */
+/* $Id: share.c,v 1.11 2002/11/29 10:49:41 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -31,7 +31,7 @@
  */
  */
 
 
 /* TODO:
 /* TODO:
- * Dynamically allocate buffer size 
+ * Dynamically allocate buffer size
  * Check wether one buffer suffices, do some performance tests
  * Check wether one buffer suffices, do some performance tests
  */
  */
 
 
@@ -43,16 +43,20 @@
 #include <sys/wait.h>
 #include <sys/wait.h>
 
 
 #include <errno.h>
 #include <errno.h>
+#include <netdb.h>
+#include <signal.h>
 #include <string.h>
 #include <string.h>
 #include <stdlib.h>
 #include <stdlib.h>
+#include <sysexits.h>
 #include <unistd.h>
 #include <unistd.h>
 
 
 #include "data.h"
 #include "data.h"
 #include "error.h"
 #include "error.h"
 #include "symuxnet.h"
 #include "symuxnet.h"
 #include "share.h"
 #include "share.h"
+#include "net.h"
 
 
-/* Shared operation: 
+/* Shared operation:
  *
  *
  * The moment the master symux receives a new packet:
  * The moment the master symux receives a new packet:
  *
  *
@@ -81,34 +85,38 @@
  */
  */
 
 
 __BEGIN_DECLS
 __BEGIN_DECLS
+int recvfd(int);
+int sendfd(int, int);
 void check_master();
 void check_master();
 void check_sem();
 void check_sem();
 void client_doneread();
 void client_doneread();
 void client_loop();
 void client_loop();
+void client_signalhandler();
 void client_waitread();
 void client_waitread();
 void exitmaster();
 void exitmaster();
 void master_resetsem();
 void master_resetsem();
 void reap_clients();
 void reap_clients();
-int  recvfd(int);
-int  sendfd(int, int);
 __END_DECLS
 __END_DECLS
 
 
-#define SEM_WAIT     0              /* wait semaphore */
-#define SEM_READ     1              /* have read semaphore */
+#define SEM_WAIT     0		/* wait semaphore */
+#define SEM_READ     1		/* have read semaphore */
 #define SEM_TOTAL    2
 #define SEM_TOTAL    2
 
 
-int   realclients;               /* number of clients active */
-int   newclients;
-int   master;                    /* is current process master or child */
-int   clientsock;                /* connected client */
+int realclients;		/* number of clients active */
+int newclients;
+int master;			/* is current process master or child */
+int clientsock;			/* connected client */
+pid_t clientpid;
 
 
-enum  ipcstat { SIPC_FREE, SIPC_KEYED, SIPC_ATTACHED };
+enum ipcstat {
+    SIPC_FREE, SIPC_KEYED, SIPC_ATTACHED
+};
 key_t shmid;
 key_t shmid;
 struct sharedregion *shm;
 struct sharedregion *shm;
 enum ipcstat shmstat;
 enum ipcstat shmstat;
 key_t semid;
 key_t semid;
 enum ipcstat semstat;
 enum ipcstat semstat;
-int   seqnr;
+int seqnr;
 /* Get start of data in shared region */
 /* Get start of data in shared region */
 long *
 long *
 shared_getmem()
 shared_getmem()
@@ -116,42 +124,43 @@ shared_getmem()
     return &shm->data;
     return &shm->data;
 }
 }
 /* Get max length of data stored in shared region */
 /* Get max length of data stored in shared region */
-long
+long 
 shared_getmaxlen()
 shared_getmaxlen()
 {
 {
     return shm->reglen - sizeof(struct sharedregion);
     return shm->reglen - sizeof(struct sharedregion);
 }
 }
 /* Set length of data stored in shared region */
 /* Set length of data stored in shared region */
-void
+void 
 shared_setlen(long length)
 shared_setlen(long length)
 {
 {
-    if (length > (shm->reglen - (long)sizeof(struct sharedregion)))
-	fatal("%s:%d: Internal error:"
+    if (length > (shm->reglen - (long) sizeof(struct sharedregion)))
+	fatal("%s:%d: internal error:"
 	      "set_length of shared region called with value larger than actual size",
 	      "set_length of shared region called with value larger than actual size",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
+
     shm->ctlen = length;
     shm->ctlen = length;
 }
 }
 /* Get length of data stored in shared region */
 /* Get length of data stored in shared region */
-long
+long 
 shared_getlen()
 shared_getlen()
 {
 {
     return shm->ctlen;
     return shm->ctlen;
 }
 }
 /* Check whether semaphore is available */
 /* Check whether semaphore is available */
-void
+void 
 check_sem()
 check_sem()
 {
 {
     if (semstat != SIPC_KEYED)
     if (semstat != SIPC_KEYED)
-	fatal("%s:%d: Internal error: Semaphore not available",
+	fatal("%s:%d: internal error: semaphore not available",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
 }
 }
 
 
 /* Check whether process is the master process */
 /* Check whether process is the master process */
-void
+void 
 check_master()
 check_master()
 {
 {
     if (master == 0)
     if (master == 0)
-	fatal("%s:%d: Internal error: Child process tried to access master routines",
+	fatal("%s:%d: internal error: child process tried to access master routines",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
 }
 }
 
 
@@ -168,11 +177,11 @@ master_resetsem()
 
 
     if ((semctl(semid, SEM_WAIT, SETVAL, semarg) != 0) ||
     if ((semctl(semid, SEM_WAIT, SETVAL, semarg) != 0) ||
 	(semctl(semid, SEM_READ, SETVAL, semarg) != 0))
 	(semctl(semid, SEM_READ, SETVAL, semarg) != 0))
-	fatal("%s:%d: Internal error: Cannot reset semaphores",
+	fatal("%s:%d: internal error: cannot reset semaphores",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
 }
 }
 /* Prepare for writing to shm */
 /* Prepare for writing to shm */
-void
+void 
 master_forbidread()
 master_forbidread()
 {
 {
     int clientsread;
     int clientsread;
@@ -180,23 +189,25 @@ master_forbidread()
 
 
     check_sem();
     check_sem();
     check_master();
     check_master();
-    
+
     /* prepare for a new read */
     /* prepare for a new read */
     semarg.val = 0;
     semarg.val = 0;
     if ((clientsread = semctl(semid, SEM_READ, GETVAL, semarg)) < 0)
     if ((clientsread = semctl(semid, SEM_READ, GETVAL, semarg)) < 0)
-	fatal("%s:%d: Internal error: Cannot read semaphore",
+	fatal("%s:%d: internal error: cannot read semaphore",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
 
 
-    if (clientsread != realclients)
+    if (clientsread != realclients) {
 	reap_clients();
 	reap_clients();
-    
+	debug("realclients = %d; clientsread = %d", realclients, clientsread);
+    }
+
     /* add new clients */
     /* add new clients */
     realclients += newclients;
     realclients += newclients;
-    newclients = 0;    
+    newclients = 0;
     master_resetsem();
     master_resetsem();
 }
 }
 /* Signal 'permit read' to all clients */
 /* Signal 'permit read' to all clients */
-void
+void 
 master_permitread()
 master_permitread()
 {
 {
     union semun semarg;
     union semun semarg;
@@ -206,12 +217,11 @@ master_permitread()
     semarg.val = realclients;
     semarg.val = realclients;
 
 
     if (semctl(semid, SEM_WAIT, SETVAL, semarg) != 0)
     if (semctl(semid, SEM_WAIT, SETVAL, semarg) != 0)
-	fatal("%s:%d: Internal error: Cannot reset semaphores",
+	fatal("%s:%d: internal error: cannot reset semaphores",
 	      __FILE__, __LINE__);
 	      __FILE__, __LINE__);
 }
 }
-
 /* Make clients wait until master signals */
 /* Make clients wait until master signals */
-void
+void 
 client_waitread()
 client_waitread()
 {
 {
     struct sembuf sops;
     struct sembuf sops;
@@ -219,37 +229,47 @@ client_waitread()
     check_sem();
     check_sem();
 
 
     sops.sem_num = SEM_WAIT;
     sops.sem_num = SEM_WAIT;
-    sops.sem_op  = -1;
+    sops.sem_op = -1;
     sops.sem_flg = 0;
     sops.sem_flg = 0;
 
 
-    if (semop(semid, &sops, 1) != 0 )
-	fatal("%s:%d: Internal error: Cannot obtain semaphore (%.200s)",
-	      __FILE__, __LINE__, strerror(errno));
+    if (semop(semid, &sops, 1) != 0)
+	fatal("%s:%d: internal error: client(%d): cannot obtain semaphore (%.200s)",
+	      __FILE__, __LINE__, clientpid, strerror(errno));
 
 
     seqnr = shm->seqnr;
     seqnr = shm->seqnr;
 }
 }
-
 /* Client signal 'done reading' to master */
 /* Client signal 'done reading' to master */
-void
+void 
 client_doneread()
 client_doneread()
 {
 {
     struct sembuf sops;
     struct sembuf sops;
 
 
     check_sem();
     check_sem();
 
 
-    if (seqnr != shm->seqnr)
-	fatal("%s:%d: Internal error: Client lagging behind (%d, %d)",
-	      __FILE__, __LINE__, seqnr, shm->seqnr);
+    if (seqnr != shm->seqnr) {
+	close(clientsock);
+	fatal("%s:%d: client(%d) lagging behind (%d, %d) = high load?",
+	      __FILE__, __LINE__, clientpid, seqnr, shm->seqnr);
+    }
 
 
     sops.sem_num = SEM_READ;
     sops.sem_num = SEM_READ;
-    sops.sem_op  = 1;
+    sops.sem_op = 1;
     sops.sem_flg = IPC_NOWAIT;
     sops.sem_flg = IPC_NOWAIT;
 
 
-    if (semop(semid, &sops, 1) != 0 )
-	fatal("%s:%d: Internal error: Cannot release semaphore (%.200s)",
+    if (semop(semid, &sops, 1) != 0)
+	fatal("%s:%d: internal error: cannot release semaphore (%.200s)",
 	      __FILE__, __LINE__, strerror(errno));
 	      __FILE__, __LINE__, strerror(errno));
-}
 
 
+    /* force scheduling by sleeping a single second */
+    sleep(1);
+}
+/* Client signal handler => always exit */
+void 
+client_signalhandler(int s)
+{
+    debug("client(%d) received signal %d - quitting", clientpid, s);
+    exit(EX_TEMPFAIL);
+}
 /* Prepare sharing structures for use */
 /* Prepare sharing structures for use */
 void 
 void 
 initshare(int bufsize)
 initshare(int bufsize)
@@ -257,7 +277,7 @@ initshare(int bufsize)
     newclients = 0;
     newclients = 0;
     realclients = 0;
     realclients = 0;
     master = 1;
     master = 1;
-    
+
     /* need some extra space for housekeeping */
     /* need some extra space for housekeeping */
     bufsize += sizeof(struct sharedregion);
     bufsize += sizeof(struct sharedregion);
 
 
@@ -267,113 +287,139 @@ initshare(int bufsize)
     atexit(exitmaster);
     atexit(exitmaster);
 
 
     if ((shmid = shmget(IPC_PRIVATE, bufsize, SHM_R | SHM_W)) < 0)
     if ((shmid = shmget(IPC_PRIVATE, bufsize, SHM_R | SHM_W)) < 0)
-	fatal("Could not get a shared memory identifier");
-    
+	fatal("could not get a shared memory identifier");
+
     shmstat = SIPC_KEYED;
     shmstat = SIPC_KEYED;
 
 
-    if ((shm = (struct sharedregion *)shmat(shmid, 0, 0)) == (void *)(-1))
-	fatal("Could not attach shared memory");
+    if ((shm = (struct sharedregion *) shmat(shmid, 0, 0)) == (void *) (-1))
+	fatal("could not attach shared memory");
 
 
     shmstat = SIPC_ATTACHED;
     shmstat = SIPC_ATTACHED;
     bzero(shm, bufsize);
     bzero(shm, bufsize);
     shm->reglen = bufsize;
     shm->reglen = bufsize;
-    
+
     /* allocate semaphores */
     /* allocate semaphores */
     if ((semid = semget(IPC_PRIVATE, SEM_TOTAL, SEM_A | SEM_R)) < 0)
     if ((semid = semget(IPC_PRIVATE, SEM_TOTAL, SEM_A | SEM_R)) < 0)
-	fatal("Could not get a semaphore");
-    
+	fatal("could not get a semaphore");
+
     semstat = SIPC_KEYED;
     semstat = SIPC_KEYED;
 
 
     master_resetsem();
     master_resetsem();
 }
 }
-
 /* Spawn off a new client */
 /* Spawn off a new client */
-void
-spawn_client(int sock) 
+pid_t
+spawn_client(int sock)
 {
 {
-    pid_t client_pid;
+    pid_t pid;
+    char peername[NI_MAXHOST];
+
     check_master();
     check_master();
 
 
-    clientsock = acceptconnection(sock);
-    
-    if ((client_pid = fork())) {
+    bzero(peername, sizeof(peername));
+    clientsock = accept_connection(sock, (char *) &peername, sizeof(peername));
+
+    if ((pid = fork())) {
 	/* server */
 	/* server */
-	newclients++;
+	if (pid == -1) {
+	    info("could not fork client process");
+	}
+	else {
+	    newclients++;
+	    info("forked client(%d) for incoming connection from %.17s",
+		 pid, peername);
+	}
+
 	close(clientsock);
 	close(clientsock);
-    } else {
+
+	return pid;
+    }
+    else {
 	/* client */
 	/* client */
 	master = 0;
 	master = 0;
+
+	/* catch signals */
+	signal(SIGHUP, client_signalhandler);
+	signal(SIGINT, client_signalhandler);
+	signal(SIGQUIT, client_signalhandler);
+	signal(SIGTERM, client_signalhandler);
+	signal(SIGTERM, client_signalhandler);
+	signal(SIGPIPE, client_signalhandler);
+
+	clientpid = getpid();
 	client_loop();
 	client_loop();
+
+	/* NOT REACHED */
+	return 0;
     }
     }
 }
 }
-
 /* Reap exit/stopped clients */
 /* Reap exit/stopped clients */
-void
+void 
 reap_clients()
 reap_clients()
 {
 {
-    pid_t clientpid;
-    int   status;
-    
+    pid_t pid;
+    int status;
+
     status = 0;
     status = 0;
 
 
     /* Reap all children that died */
     /* Reap all children that died */
-    while (((int)(clientpid = wait4(-1, &status, WNOHANG, NULL)) > 0) && realclients >= 0) {
+    while (((int) (pid = wait4(-1, &status, WNOHANG, NULL)) > 0) && realclients >= 0) {
 
 
-      /* wait4 is supposed to return 0 if there is no status to report, but
-	 it also reports -1 on OpenBSD 2.9 */
+	/*
+	 * wait4 is supposed to return 0 if there is no status to report, but
+	 * it also reports -1 on OpenBSD 2.9
+	 */
 
 
 	if (WIFEXITED(status))
 	if (WIFEXITED(status))
-	    info("client process %d exited", clientpid, status);
+	    info("client process %d exited", pid, status);
 	if (WIFSIGNALED(status))
 	if (WIFSIGNALED(status))
-	    info("client process %d killed with signal %d", clientpid, WTERMSIG(status));
+	    info("client process %d killed with signal %d", pid, WTERMSIG(status));
 	if (WIFSTOPPED(status))
 	if (WIFSTOPPED(status))
-	    info("client process %d stopped with signal %d", clientpid, WSTOPSIG(status));
+	    info("client process %d stopped with signal %d", pid, WSTOPSIG(status));
 
 
 	realclients--;
 	realclients--;
     }
     }
 }
 }
-
 /* Remove shared memory and semaphores at exit */
 /* Remove shared memory and semaphores at exit */
 void 
 void 
-exitmaster() 
+exitmaster()
 {
 {
     union semun semarg;
     union semun semarg;
 
 
     if (master == 0)
     if (master == 0)
 	return;
 	return;
-	
+
     switch (shmstat) {
     switch (shmstat) {
     case SIPC_ATTACHED:
     case SIPC_ATTACHED:
 	if (shmdt(shm))
 	if (shmdt(shm))
-	    warning("%s:%d: Internal error: control region could not be detached",
+	    warning("%s:%d: internal error: control region could not be detached",
 		    __FILE__, __LINE__);
 		    __FILE__, __LINE__);
 
 
 	/* no break */
 	/* no break */
     case SIPC_KEYED:
     case SIPC_KEYED:
 	if (shmctl(shmid, IPC_RMID, NULL))
 	if (shmctl(shmid, IPC_RMID, NULL))
-	    warning("%s:%d: Internal error: could remove control region %d",
+	    warning("%s:%d: internal error: could remove control region %d",
 		    __FILE__, __LINE__, shmid);
 		    __FILE__, __LINE__, shmid);
 	/* no break */
 	/* no break */
     case SIPC_FREE:
     case SIPC_FREE:
 	break;
 	break;
 
 
     default:
     default:
-	warning("%s:%d: Internal error: control region is in an unknown state",
+	warning("%s:%d: internal error: control region is in an unknown state",
 		__FILE__, __LINE__);
 		__FILE__, __LINE__);
     }
     }
 
 
     switch (semstat) {
     switch (semstat) {
     case SIPC_KEYED:
     case SIPC_KEYED:
 	semarg.val = 0;
 	semarg.val = 0;
-	if (semctl(semid, 0, IPC_RMID, semarg) != 0) 
-	    warning("%s:%d: Internal error: could not remove semaphore %d",
+	if (semctl(semid, 0, IPC_RMID, semarg) != 0)
+	    warning("%s:%d: internal error: could not remove semaphore %d",
 		    __FILE__, __LINE__, semid);
 		    __FILE__, __LINE__, semid);
 	/* no break */
 	/* no break */
     case SIPC_FREE:
     case SIPC_FREE:
 	break;
 	break;
 
 
     default:
     default:
-	warning("%s:%d: Internal error: semaphore is in an unknown state",
+	warning("%s:%d: internal error: semaphore is in an unknown state",
 		__FILE__, __LINE__);
 		__FILE__, __LINE__);
     }
     }
 }
 }
@@ -384,25 +430,25 @@ client_loop()
     int sent;
     int sent;
     int written;
     int written;
 
 
-    for (;;) { /* FOREVER */
-	
+    for (;;) {			/* FOREVER */
+
 	client_waitread();
 	client_waitread();
-	
+
 	total = shared_getlen();
 	total = shared_getlen();
 	sent = 0;
 	sent = 0;
 
 
 	while (sent < total) {
 	while (sent < total) {
-	  
-	  if ((written = write(clientsock, (char *)(shared_getmem() + sent), total - sent)) == -1) {
-	    info("Write error. Client will quit.");
-	    exit(1);
-	  }
-	  
-	  sent += written;
-	  
-	  debug("client written %d bytes of %d total", sent, total);
+
+	    if ((written = write(clientsock, (char *) (shared_getmem() + sent), total - sent)) == -1) {
+		info("client(%d): write error. Client will quit.", clientpid);
+		exit(1);
+	    }
+
+	    sent += written;
+
+	    debug("client(%d): written %d bytes of %d total", clientpid, sent, total);
 	}
 	}
-	
+
 	client_doneread();
 	client_doneread();
     }
     }
 }
 }

+ 15 - 14
symon/symux/share.h

@@ -1,4 +1,4 @@
-/* $Id: share.h,v 1.4 2002/09/14 15:54:55 dijkstra Exp $ */
+/* $Id: share.h,v 1.6 2002/11/29 10:49:41 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -31,7 +31,7 @@
  */
  */
 
 
 /* TODO:
 /* TODO:
- * Dynamically allocate buffer size 
+ * Dynamically allocate buffer size
  * Check wether one buffer suffices, do some performance tests
  * Check wether one buffer suffices, do some performance tests
  */
  */
 
 
@@ -41,27 +41,28 @@
 #include "data.h"
 #include "data.h"
 
 
 /* Share contains all routines needed for the ipc between symuxes */
 /* Share contains all routines needed for the ipc between symuxes */
-#define SEM_WAIT     0              /* wait semaphore */
-#define SEM_READ     1              /* have read semaphore */
+#define SEM_WAIT     0		/* wait semaphore */
+#define SEM_READ     1		/* have read semaphore */
 #define SEM_TOTAL    2
 #define SEM_TOTAL    2
 
 
 struct sharedregion {
 struct sharedregion {
     long seqnr;
     long seqnr;
-    long reglen;                   /* size of buffer */
-    long ctlen;                    /* amount of content in buffer, assert(< size) */
+    long reglen;		/* size of buffer */
+    long ctlen;			/* amount of content in buffer, assert(<
+				 * size) */
     long data;
     long data;
 };
 };
 
 
 /* prototypes */
 /* prototypes */
 __BEGIN_DECLS
 __BEGIN_DECLS
-void  master_forbidread();
-void  master_permitread();
-long  shared_getlen();
-long  shared_getmaxlen();
+void master_forbidread();
+void master_permitread();
+long shared_getlen();
+long shared_getmaxlen();
 long *shared_getmem();
 long *shared_getmem();
-void  initshare();
-void  shared_setlen(long);
-void  spawn_client(int);
+void initshare();
+void shared_setlen(long);
+pid_t spawn_client(int);
 __END_DECLS
 __END_DECLS
 
 
-#endif /*_SYMUX_SHARE_H*/
+#endif				/* _SYMUX_SHARE_H */

+ 20 - 15
symon/symux/symux.8

@@ -84,23 +84,26 @@ instead of
 .Nm
 .Nm
 obtains configuration data from 
 obtains configuration data from 
 .Pa /etc/symux.conf .
 .Pa /etc/symux.conf .
-The configuration file contains one mux stanza that defines on what interface and port
+The configuration file contains one mux stanza that defines on what host address and port
 .Nm 
 .Nm 
 should listen to for incoming monitored data. There is a source section for
 should listen to for incoming monitored data. There is a source section for
 every host that is to be monitored. The source section defines what data to
 every host that is to be monitored. The source section defines what data to
-accept and where to write that data to. Whitespace, newlines and text behind
-'#' are ignored. The format in BNF:
+accept and where to write that data to. In the case that a source is of another
+address family than the mux stanza, i.e. source = ipv6 with mux = ipv4, a
+listen port of the sources' family is opened using the unspecified
+address. Whitespace, newlines and text behind '#' are ignored. The format in
+BNF:
 .Pp
 .Pp
 .nf
 .nf
 stmt         = mux-stmt | source-stmt
 stmt         = mux-stmt | source-stmt
 mux-stmt     = "mux" host [ port ]
 mux-stmt     = "mux" host [ port ]
-host         = ip4addr | hostname
-port         = [ "port" | ":" | "," ] portnumber
+host         = ip4addr | ip6addr | hostname
+port         = [ "port" | "," ] portnumber
 source-stmt  = "source" host "{" accept-stmts write-stmts [ datadir-stmt ] "}"
 source-stmt  = "source" host "{" accept-stmts write-stmts [ datadir-stmt ] "}"
 accept-stmts = accept-stmt [accept-stmts]
 accept-stmts = accept-stmt [accept-stmts]
 accept-stmt  = "accept" "{" resources "}"
 accept-stmt  = "accept" "{" resources "}"
 resources    = resource ["(" argument ")"] [ ","|" " resources ]
 resources    = resource ["(" argument ")"] [ ","|" " resources ]
-resource     = "cpu" | "mem" | "if" | "io" | "pf"
+resource     = "cpu" | "mem" | "if" | "io" | "pf" | "debug"
 argument     = number | interfacename | diskname
 argument     = number | interfacename | diskname
 datadir-stmt = "datadir" dirname
 datadir-stmt = "datadir" dirname
 write-stmts  = write-stmt [write-stmts]
 write-stmts  = write-stmt [write-stmts]
@@ -133,7 +136,7 @@ on localhost.
 will also listen on tcp port 2100 for incoming listeners.
 will also listen on tcp port 2100 for incoming listeners.
 .Pp
 .Pp
 .nf
 .nf
-mux 127.0.0.1:2100
+mux 127.0.0.1 2100
 source 127.0.0.1 {
 source 127.0.0.1 {
     accept { cpu(0), mem, pf,
     accept { cpu(0), mem, pf,
              if(xl0), if(de0),
              if(xl0), if(de0),
@@ -188,19 +191,19 @@ The format is
 Data formats:
 Data formats:
 .Bl -tag -width Ds
 .Bl -tag -width Ds
 .It cpu
 .It cpu
-Time spent in (user, nice, system, interrupt, idle). Total time is 100, data is
-offered with precision 2.
+Time spent in ( user, nice, system, interrupt, idle ). Total time is 100, data
+is offered with precision 2.
 .It mem
 .It mem
-Memory in (real active, real total, free, swap used, swap total). All values
+Memory in ( real_active, real_total, free, swap_used, swap_total ). All values
 are in bytes rounded of to page boundaries. Values are 32 bit unsigned integers
 are in bytes rounded of to page boundaries. Values are 32 bit unsigned integers
 internally.
 internally.
 .It if
 .It if
-Interface counters (packets in, packets out, bytes in, bytes out, multicasts
-in, multicasts out, errors in, errors out, collisions, drops). Values are 32
-bit unsigned integers internally.
+Interface counters ( packets_in, packets_out, bytes_in, bytes_out,
+multicasts_in, multicasts_out, errors_in, errors_out, collisions, drops
+). Values are 32 bit unsigned integers internally.
 .It io
 .It io
-Io/disk counters (total transfers, total seeks, total bytes). Values are 64 bit
-unsigned integers internally.
+Io/disk counters ( total_transfers, total_seeks, total_bytes ). Values are 64
+bit unsigned integers internally.
 .It pf
 .It pf
 Packet filter statistics ( bytes_v4_in : bytes_v4_out : bytes_v6_in :
 Packet filter statistics ( bytes_v4_in : bytes_v4_out : bytes_v6_in :
 bytes_v6_out : packets_v4_in_pass : packets_v4_in_drop : packets_v4_out_pass :
 bytes_v6_out : packets_v4_in_pass : packets_v4_in_drop : packets_v4_out_pass :
@@ -209,6 +212,8 @@ packets_v6_out_pass : packets_v6_out_drop : states_entries : states_searches :
 states_inserts : states_removals : counters_match : counters_badoffset :
 states_inserts : states_removals : counters_match : counters_badoffset :
 counters_fragment : counters_short : counters_normalize : counters_memory
 counters_fragment : counters_short : counters_normalize : counters_memory
 ). Values are 64 bit unsigned integers internally.
 ). Values are 64 bit unsigned integers internally.
+.It debug
+Kernel variables debug0 to debug19. ( debug0 : ... : debug19 ). Values are 32 bit unsigned integers. 
 .El
 .El
 .Sh SIGNALS
 .Sh SIGNALS
 .Bl -tag -width Ds
 .Bl -tag -width Ds

+ 80 - 71
symon/symux/symux.c

@@ -1,4 +1,4 @@
-/* $Id: symux.c,v 1.24 2002/10/18 12:30:48 dijkstra Exp $ */
+/* $Id: symux.c,v 1.26 2002/11/29 10:45:22 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -7,7 +7,7 @@
  * Redistribution and use in source and binary forms, with or without
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * modification, are permitted provided that the following conditions
  * are met:
  * are met:
- 
+ *
  *    - Redistributions of source code must retain the above copyright
  *    - Redistributions of source code must retain the above copyright
  *      notice, this list of conditions and the following disclaimer.
  *      notice, this list of conditions and the following disclaimer.
  *    - Redistributions in binary form must reproduce the above
  *    - Redistributions in binary form must reproduce the above
@@ -64,29 +64,31 @@ int flag_hup = 0;
 fd_set fdset;
 fd_set fdset;
 int maxfd;
 int maxfd;
 
 
-void
-exithandler(int s) {
+void 
+exithandler(int s)
+{
     info("received signal %d - quitting", s);
     info("received signal %d - quitting", s);
     exit(EX_TEMPFAIL);
     exit(EX_TEMPFAIL);
 }
 }
-void
-huphandler(int s) {
+void 
+huphandler(int s)
+{
     info("hup received");
     info("hup received");
     flag_hup = 1;
     flag_hup = 1;
 }
 }
-/* 
+/*
  * symux is the receiver of symon performance measurements.
  * symux is the receiver of symon performance measurements.
  *
  *
  * The main goals symon hopes to accomplish is:
  * The main goals symon hopes to accomplish is:
- * - to take fine grained measurements of system parameters 
- * - with minimal performance impact 
+ * - to take fine grained measurements of system parameters
+ * - with minimal performance impact
  * - in a secure way.
  * - in a secure way.
- * 
+ *
  * Measuring system parameters (e.g. interfaces) sometimes means traversing
  * Measuring system parameters (e.g. interfaces) sometimes means traversing
  * lists in kernel memory. Because of this the measurement of data has been
  * lists in kernel memory. Because of this the measurement of data has been
  * decoupled from the processing and storage of data. Storing the measured
  * decoupled from the processing and storage of data. Storing the measured
  * information that symon provides is done by a second program, called symux.
  * information that symon provides is done by a second program, called symux.
- * 
+ *
  * Symon can keep track of cpu, memory, disk and network interface
  * Symon can keep track of cpu, memory, disk and network interface
  * interactions. Symon was built specifically for OpenBSD.
  * interactions. Symon was built specifically for OpenBSD.
  */
  */
@@ -101,7 +103,6 @@ main(int argc, char *argv[])
     char *stringptr;
     char *stringptr;
     int maxstringlen;
     int maxstringlen;
     struct muxlist mul, newmul;
     struct muxlist mul, newmul;
-    struct sourcelist sol, newsol;
     char *arg_ra[4];
     char *arg_ra[4];
     struct stream *stream;
     struct stream *stream;
     struct source *source;
     struct source *source;
@@ -113,11 +114,10 @@ main(int argc, char *argv[])
     int churnbuflen;
     int churnbuflen;
 
 
     SLIST_INIT(&mul);
     SLIST_INIT(&mul);
-    SLIST_INIT(&sol);
-	
+
     /* reset flags */
     /* reset flags */
     flag_debug = 0;
     flag_debug = 0;
-    flag_daemon = 0;    
+    flag_daemon = 0;
     cfgfile = SYMUX_CONFIG_FILE;
     cfgfile = SYMUX_CONFIG_FILE;
 
 
     while ((ch = getopt(argc, argv, "dvf:")) != -1) {
     while ((ch = getopt(argc, argv, "dvf:")) != -1) {
@@ -130,7 +130,7 @@ main(int argc, char *argv[])
 		/* cfg path needs to be absolute, we will be a daemon soon */
 		/* cfg path needs to be absolute, we will be a daemon soon */
 		if ((cfgpath = getwd(NULL)) == NULL)
 		if ((cfgpath = getwd(NULL)) == NULL)
 		    fatal("could not get working directory");
 		    fatal("could not get working directory");
-		
+
 		maxstringlen = strlen(cfgpath) + strlen(optarg) + 1;
 		maxstringlen = strlen(cfgpath) + strlen(optarg) + 1;
 		cfgfile = xmalloc(maxstringlen);
 		cfgfile = xmalloc(maxstringlen);
 		strncpy(cfgfile, cfgpath, maxstringlen);
 		strncpy(cfgfile, cfgpath, maxstringlen);
@@ -141,7 +141,8 @@ main(int argc, char *argv[])
 		cfgfile[maxstringlen] = '\0';
 		cfgfile[maxstringlen] = '\0';
 
 
 		free(cfgpath);
 		free(cfgpath);
-	    } else 
+	    }
+	    else
 		cfgfile = xstrdup(optarg);
 		cfgfile = xstrdup(optarg);
 
 
 	    break;
 	    break;
@@ -154,16 +155,16 @@ main(int argc, char *argv[])
     }
     }
 
 
     /* parse configuration file */
     /* parse configuration file */
-    if (!read_config_file(&mul, &sol, cfgfile))
+    if (!read_config_file(&mul, cfgfile))
 	fatal("configuration contained errors; quitting");
 	fatal("configuration contained errors; quitting");
 
 
     setegid(getgid());
     setegid(getgid());
     setgid(getgid());
     setgid(getgid());
 
 
     if (flag_debug != 1) {
     if (flag_debug != 1) {
-	if (daemon(0,0) != 0)
+	if (daemon(0, 0) != 0)
 	    fatal("daemonize failed");
 	    fatal("daemonize failed");
-	
+
 	flag_daemon = 1;
 	flag_daemon = 1;
 
 
 	/* record pid */
 	/* record pid */
@@ -172,8 +173,8 @@ main(int argc, char *argv[])
 	    fprintf(f, "%u\n", (u_int) getpid());
 	    fprintf(f, "%u\n", (u_int) getpid());
 	    fclose(f);
 	    fclose(f);
 	}
 	}
-    } 
-    
+    }
+
     info("symux version %s", SYMUX_VERSION);
     info("symux version %s", SYMUX_VERSION);
 
 
     if (flag_debug == 1)
     if (flag_debug == 1)
@@ -181,81 +182,84 @@ main(int argc, char *argv[])
 
 
     mux = SLIST_FIRST(&mul);
     mux = SLIST_FIRST(&mul);
 
 
-    churnbuflen = calculate_churnbuffer(&sol);
+    churnbuflen = calculate_churnbuffer(&mux->sol);
     debug("size of churnbuffer = %d", churnbuflen);
     debug("size of churnbuffer = %d", churnbuflen);
     initshare(churnbuflen);
     initshare(churnbuflen);
 
 
     /* catch signals */
     /* catch signals */
     signal(SIGHUP, huphandler);
     signal(SIGHUP, huphandler);
-    signal(SIGINT, exithandler); 
-    signal(SIGQUIT, exithandler); 
+    signal(SIGINT, exithandler);
+    signal(SIGQUIT, exithandler);
+    signal(SIGTERM, exithandler);
     signal(SIGTERM, exithandler);
     signal(SIGTERM, exithandler);
-    signal(SIGTERM, exithandler); 
 
 
     /* prepare crc32 */
     /* prepare crc32 */
     init_crc32();
     init_crc32();
 
 
-    getsymonsocket(mux);
-    getclientsocket(mux);
+    /* prepare sockets */
+    if (get_symon_sockets(mux) == 0)
+	fatal("no sockets could be opened for incoming symon traffic");
+    if (get_client_socket(mux) == 0)
+	fatal("socket for client connections could not be opened");
 
 
-    for (;;) {
-	waitfortraffic(mux, &sol, &source, &packet);
+    /* main loop */
+    for (;;) {			/* FOREVER */
+	wait_for_traffic(mux, &source, &packet);
 
 
 	if (flag_hup == 1) {
 	if (flag_hup == 1) {
 	    flag_hup = 0;
 	    flag_hup = 0;
 
 
 	    SLIST_INIT(&newmul);
 	    SLIST_INIT(&newmul);
-	    SLIST_INIT(&newsol);
 
 
-	    if (!read_config_file(&newmul, &newsol, cfgfile)) {
+	    if (!read_config_file(&newmul, cfgfile)) {
 		info("new configuration contains errors; keeping old configuration");
 		info("new configuration contains errors; keeping old configuration");
 		free_muxlist(&newmul);
 		free_muxlist(&newmul);
-		free_sourcelist(&newsol);
-	    } else {
+	    }
+	    else {
 		info("read configuration file '%.100s' succesfully", cfgfile);
 		info("read configuration file '%.100s' succesfully", cfgfile);
 		free_muxlist(&mul);
 		free_muxlist(&mul);
-		free_sourcelist(&sol);
 		mul = newmul;
 		mul = newmul;
-		sol = newsol;
 		mux = SLIST_FIRST(&mul);
 		mux = SLIST_FIRST(&mul);
-		getsymonsocket(mux);
-		getclientsocket(mux);
+		get_symon_sockets(mux);
+		get_client_socket(mux);
 	    }
 	    }
-	} else {
+	}
+	else {
 
 
-	    /* Put information from packet into stringbuf (shared region). Note
-	     * that the stringbuf is used twice: 1) to update the rrdfile and 2) to
-	     * collect all the data from a single packet that needs to shared to
-	     * the clients. This is the reason for the hasseling with stringptr.
+	    /*
+	     * Put information from packet into stringbuf (shared region).
+	     * Note that the stringbuf is used twice: 1) to update the
+	     * rrdfile and 2) to collect all the data from a single packet
+	     * that needs to shared to the clients. This is the reason for
+	     * the hasseling with stringptr.
 	     */
 	     */
-	    
+
 	    offset = mux->offset;
 	    offset = mux->offset;
 	    maxstringlen = shared_getmaxlen();
 	    maxstringlen = shared_getmaxlen();
 	    /* put time:ip: into shared region */
 	    /* put time:ip: into shared region */
 	    master_forbidread();
 	    master_forbidread();
 	    timestamp = (time_t) packet.header.timestamp;
 	    timestamp = (time_t) packet.header.timestamp;
-	    stringbuf = (char *)shared_getmem();
-	    snprintf(stringbuf, maxstringlen, "%u.%u.%u.%u;",
-		     IPAS4BYTES(source->ip));
-	    
+	    stringbuf = (char *) shared_getmem();
+	    snprintf(stringbuf, maxstringlen, "%s;", source->addr);
+
 	    /* hide this string region from rrd update */
 	    /* hide this string region from rrd update */
 	    maxstringlen -= strlen(stringbuf);
 	    maxstringlen -= strlen(stringbuf);
 	    stringptr = stringbuf + strlen(stringbuf);
 	    stringptr = stringbuf + strlen(stringbuf);
-	    
+
 	    while (offset < packet.header.length) {
 	    while (offset < packet.header.length) {
 		bzero(&ps, sizeof(struct packedstream));
 		bzero(&ps, sizeof(struct packedstream));
 		offset += sunpack(packet.data + offset, &ps);
 		offset += sunpack(packet.data + offset, &ps);
-		
+
 		/* find stream in source */
 		/* find stream in source */
 		stream = find_source_stream(source, ps.type, ps.args);
 		stream = find_source_stream(source, ps.type, ps.args);
-		
+
 		if (stream != NULL) {
 		if (stream != NULL) {
 		    /* put type in and hide from rrd */
 		    /* put type in and hide from rrd */
 		    snprintf(stringptr, maxstringlen, "%s:", type2str(ps.type));
 		    snprintf(stringptr, maxstringlen, "%s:", type2str(ps.type));
 		    maxstringlen -= strlen(stringptr);
 		    maxstringlen -= strlen(stringptr);
 		    stringptr += strlen(stringptr);
 		    stringptr += strlen(stringptr);
 		    /* put arguments in and hide from rrd */
 		    /* put arguments in and hide from rrd */
-		    snprintf(stringptr, maxstringlen, "%s:", 
+		    snprintf(stringptr, maxstringlen, "%s:",
 			     ((ps.args == NULL) ? "0" : ps.args));
 			     ((ps.args == NULL) ? "0" : ps.args));
 		    maxstringlen -= strlen(stringptr);
 		    maxstringlen -= strlen(stringptr);
 		    stringptr += strlen(stringptr);
 		    stringptr += strlen(stringptr);
@@ -264,10 +268,10 @@ main(int argc, char *argv[])
 		    arg_ra[3] = stringptr;
 		    arg_ra[3] = stringptr;
 		    maxstringlen -= strlen(stringptr);
 		    maxstringlen -= strlen(stringptr);
 		    stringptr += strlen(stringptr);
 		    stringptr += strlen(stringptr);
-		    
+
 		    /* put measurements in */
 		    /* put measurements in */
 		    ps2strn(&ps, stringptr, maxstringlen, PS2STR_RRD);
 		    ps2strn(&ps, stringptr, maxstringlen, PS2STR_RRD);
-		    
+
 		    if (stream->file != NULL) {
 		    if (stream->file != NULL) {
 			/* clear optind for getopt call by rrdupdate */
 			/* clear optind for getopt call by rrdupdate */
 			optind = 0;
 			optind = 0;
@@ -275,41 +279,46 @@ main(int argc, char *argv[])
 			arg_ra[0] = "rrdupdate";
 			arg_ra[0] = "rrdupdate";
 			arg_ra[1] = "--";
 			arg_ra[1] = "--";
 			arg_ra[2] = stream->file;
 			arg_ra[2] = stream->file;
-			
-			/* This call will cost a lot (symux will become
+
+			/*
+			 * This call will cost a lot (symux will become
 			 * unresponsive and eat up massive amounts of cpu) if
 			 * unresponsive and eat up massive amounts of cpu) if
-			 * the rrdfile is out of sync. While I could update the
-			 * rrd in a separate process, I choose not to at this
-			 * time.  
+			 * the rrdfile is out of sync. While I could update
+			 * the rrd in a separate process, I choose not to at
+			 * this time.
 			 */
 			 */
 			rrd_update(4, arg_ra);
 			rrd_update(4, arg_ra);
-			
+
 			if (rrd_test_error()) {
 			if (rrd_test_error()) {
 			    warning("rrd_update:%s", rrd_get_error());
 			    warning("rrd_update:%s", rrd_get_error());
-			    warning("%s %s %s %s", arg_ra[0], arg_ra[1], 
+			    warning("%s %s %s %s", arg_ra[0], arg_ra[1],
 				    arg_ra[2], arg_ra[3]);
 				    arg_ra[2], arg_ra[3]);
-			    rrd_clear_error();                                                            
-			} else {
-			    if (flag_debug == 1) 
-				debug("%s %s %s %s", arg_ra[0], arg_ra[1], 
+			    rrd_clear_error();
+			}
+			else {
+			    if (flag_debug == 1)
+				debug("%s %s %s %s", arg_ra[0], arg_ra[1],
 				      arg_ra[2], arg_ra[3]);
 				      arg_ra[2], arg_ra[3]);
 			}
 			}
 		    }
 		    }
 		    maxstringlen -= strlen(stringptr);
 		    maxstringlen -= strlen(stringptr);
 		    stringptr += strlen(stringptr);
 		    stringptr += strlen(stringptr);
 		    snprintf(stringptr, maxstringlen, ";");
 		    snprintf(stringptr, maxstringlen, ";");
-		maxstringlen -= strlen(stringptr);
-		stringptr += strlen(stringptr);
+		    maxstringlen -= strlen(stringptr);
+		    stringptr += strlen(stringptr);
 		}
 		}
 	    }
 	    }
-	    /* packet = parsed and in ascii in shared region -> copy to clients */
+	    /*
+	     * packet = parsed and in ascii in shared region -> copy to
+	     * clients
+	     */
 	    snprintf(stringptr, maxstringlen, "\n");
 	    snprintf(stringptr, maxstringlen, "\n");
 	    stringptr += strlen(stringptr);
 	    stringptr += strlen(stringptr);
 	    shared_setlen((stringptr - stringbuf));
 	    shared_setlen((stringptr - stringbuf));
-	    debug("Churnbuffer used: %d", (stringptr - stringbuf));
+	    debug("churnbuffer used: %d", (stringptr - stringbuf));
 	    master_permitread();
 	    master_permitread();
-	} /* flag_hup == 0 */
-    } /* forever */
+	}			/* flag_hup == 0 */
+    }				/* forever */
 
 
     /* NOT REACHED */
     /* NOT REACHED */
     return (EX_SOFTWARE);
     return (EX_SOFTWARE);

+ 2 - 2
symon/symux/symux.conf

@@ -1,9 +1,9 @@
 #
 #
-# $Id: symux.conf,v 1.19 2002/10/25 15:25:08 dijkstra Exp $
+# $Id: symux.conf,v 1.20 2002/11/29 10:49:41 dijkstra Exp $
 #
 #
 # Demo symux configuration. See symux(8) for BNF.
 # Demo symux configuration. See symux(8) for BNF.
 
 
-mux 10.0.0.1:2100
+mux 10.0.0.1 2100
 
 
 source 10.0.0.1 {
 source 10.0.0.1 {
 	accept { cpu(0), mem, if(xl0), if(de0),
 	accept { cpu(0), mem, if(xl0), if(de0),

+ 3 - 3
symon/symux/symux.h

@@ -1,4 +1,4 @@
-/* $Id: symux.h,v 1.15 2002/10/18 12:30:48 dijkstra Exp $ */
+/* $Id: symux.h,v 1.16 2002/11/29 10:45:22 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -37,7 +37,7 @@
 
 
 #define SYMUX_PID_FILE "/var/run/symux.pid"
 #define SYMUX_PID_FILE "/var/run/symux.pid"
 
 
-/* Amount of connections allowed in listen backlog 
+/* Amount of connections allowed in listen backlog
  * - note that more than 128 makes no sense in OpenBSD
  * - note that more than 128 makes no sense in OpenBSD
  */
  */
 #define SYMUX_TCPBACKLOG 5
 #define SYMUX_TCPBACKLOG 5
@@ -45,4 +45,4 @@
 /* Number of retries allowed in recvfrom */
 /* Number of retries allowed in recvfrom */
 #define SYMUX_MAXREADTRIES 5
 #define SYMUX_MAXREADTRIES 5
 
 
-#endif /*_SYMUX_SYMUX_H*/
+#endif				/* _SYMUX_SYMUX_H */

+ 158 - 98
symon/symux/symuxnet.c

@@ -1,4 +1,4 @@
-/* $Id: symuxnet.c,v 1.10 2002/09/14 15:54:56 dijkstra Exp $ */
+/* $Id: symuxnet.c,v 1.12 2002/11/29 10:45:22 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -32,10 +32,10 @@
 
 
 #include <sys/types.h>
 #include <sys/types.h>
 #include <sys/socket.h>
 #include <sys/socket.h>
-#include <netinet/in.h>
 
 
 #include <errno.h>
 #include <errno.h>
 #include <fcntl.h>
 #include <fcntl.h>
+#include <netdb.h>
 #include <string.h>
 #include <string.h>
 #include <unistd.h>
 #include <unistd.h>
 
 
@@ -47,59 +47,95 @@
 #include "xmalloc.h"
 #include "xmalloc.h"
 #include "share.h"
 #include "share.h"
 
 
-/* Obtain a udp socket for incoming symon traffic */
+__BEGIN_DECLS
+int check_crc_packet(struct symonpacket *);
+__END_DECLS
+
+/* Obtain sockets for incoming symon traffic */
 int 
 int 
-getsymonsocket(struct mux *mux) 
+get_symon_sockets(struct mux * mux)
 {
 {
-    struct sockaddr_in sockaddr;
-    int sock;
-    
-    if ((sock = socket(AF_INET, SOCK_DGRAM, 0)) == -1) 
-	fatal("could not obtain socket: %.200s", strerror(errno));
+    struct source *source;
+    struct sockaddr_storage sockaddr;
+    int family, nsocks;
+    char hbuf[NI_MAXHOST], sbuf[NI_MAXSERV];
+    nsocks = 0;
 
 
-    sockaddr.sin_family = AF_INET;
-    sockaddr.sin_port = htons(mux->port);
-    sockaddr.sin_addr.s_addr = htonl(mux->ip);
-    bzero(&sockaddr.sin_zero, sizeof(sockaddr.sin_zero));
+    /* generate the udp listen socket specified in the mux statement */
+    get_mux_sockaddr(mux, SOCK_DGRAM);
 
 
-    if (bind(sock, (struct sockaddr *) &sockaddr, 
-	     sizeof(struct sockaddr)) == -1)
-	fatal("could not bind socket: %.200s", strerror(errno));
+    /* iterate over our sources to determine what types of sockets we need */
+    SLIST_FOREACH(source, &mux->sol, sources) {
+	get_source_sockaddr(source);
 
 
-    mux->symonsocket = sock;
+	family = source->sockaddr.ss_family;
+	/* do we have a socket for this type of family */
+	if (mux->symonsocket[family] <= 0) {
+	    if ((mux->symonsocket[family] = socket(family, SOCK_DGRAM, 0)) != -1) {
+		/*
+		 * does the mux statement specify a specific destination
+		 * address
+		 */
+		if (mux->sockaddr.ss_family == family) {
+		    cpysock((struct sockaddr *) & mux->sockaddr, &sockaddr);
+		}
+		else {
+		    get_inaddrany_sockaddr(&sockaddr, family, SOCK_DGRAM, mux->port);
+		}
 
 
-    info("listening for incoming symon traffic on udp:%s:%d", 
-	 mux->name, mux->port);
+		if (bind(mux->symonsocket[family], (struct sockaddr *) & sockaddr,
+			 sockaddr.ss_len) == -1)
+		    close(mux->symonsocket[family]);
+		else {
+		    if (getnameinfo((struct sockaddr *) & sockaddr, sockaddr.ss_len,
+				    hbuf, sizeof(hbuf), sbuf, sizeof(sbuf),
+				    NI_NUMERICHOST | NI_NUMERICSERV)) {
+			info("getnameinfo error - cannot determine numeric hostname and service");
+			info("listening for incoming symon traffic for family %d", family);
+		    }
+		    else
+			info("listening for incoming symon traffic on udp %s %s", hbuf, sbuf);
 
 
-    return sock;
+		    nsocks++;
+		}
+	    }
+	}
+    }
+    return nsocks;
 }
 }
 /* Obtain a listen socket for new clients */
 /* Obtain a listen socket for new clients */
-int
-getclientsocket(struct mux *mux)
+int 
+get_client_socket(struct mux * mux)
 {
 {
-  struct sockaddr_in sockaddr;
-  int sock;
-  
-  if ((sock = socket(AF_INET, SOCK_STREAM, 0)) == -1)
+    struct addrinfo hints, *res;
+    int error, sock;
+
+    if ((sock = socket(mux->sockaddr.ss_family, SOCK_STREAM, 0)) == -1)
 	fatal("could not obtain socket: %.200s", strerror(errno));
 	fatal("could not obtain socket: %.200s", strerror(errno));
 
 
-    sockaddr.sin_family = AF_INET;
-    sockaddr.sin_port = htons(mux->port);
-    sockaddr.sin_addr.s_addr = htonl(mux->ip);
-    bzero(&sockaddr.sin_zero, sizeof(sockaddr.sin_zero));
+    bzero((void *) &hints, sizeof(struct addrinfo));
 
 
-    if (bind(sock, (struct sockaddr *) &sockaddr, 
-	     sizeof(struct sockaddr)) == -1)
+    hints.ai_family = mux->sockaddr.ss_family;
+    hints.ai_flags = AI_PASSIVE | AI_NUMERICHOST;
+    hints.ai_socktype = SOCK_STREAM;
+
+    if ((error = getaddrinfo(mux->addr, mux->port, &hints, &res)) != 0)
+	fatal("could not get address information for %s:%s - %s",
+	      mux->addr, mux->port, gai_strerror(error));
+
+    if (bind(sock, (struct sockaddr *) res->ai_addr, res->ai_addrlen) == -1)
 	fatal("could not bind socket: %.200s", strerror(errno));
 	fatal("could not bind socket: %.200s", strerror(errno));
 
 
+    freeaddrinfo(res);
+
     if (listen(sock, SYMUX_TCPBACKLOG) == -1)
     if (listen(sock, SYMUX_TCPBACKLOG) == -1)
-      fatal("could not listen to socket: %.200s", strerror(errno));
+	fatal("could not listen to socket: %.200s", strerror(errno));
 
 
     fcntl(sock, O_NONBLOCK);
     fcntl(sock, O_NONBLOCK);
     mux->clientsocket = sock;
     mux->clientsocket = sock;
 
 
-    info("listening for incoming connections on tcp:%s:%d", 
-	 mux->name, mux->port);
+    info("listening for incoming connections on tcp %s %s",
+	 mux->addr, mux->port);
 
 
     return sock;
     return sock;
 }
 }
@@ -108,86 +144,97 @@ getclientsocket(struct mux *mux)
  * Returns the <source> and <packet>
  * Returns the <source> and <packet>
  * Silently forks off clienthandlers
  * Silently forks off clienthandlers
  */
  */
-void
-waitfortraffic(struct mux *mux, struct sourcelist *sourcelist, 
-	       struct source **source, struct symonpacket *packet) 
+void 
+wait_for_traffic(struct mux * mux, struct source ** source,
+		 struct symonpacket * packet)
 {
 {
     fd_set readset;
     fd_set readset;
+    int i;
     int socksactive;
     int socksactive;
     int maxsock;
     int maxsock;
 
 
-    maxsock = ((mux->clientsocket > mux->symonsocket) ?
-	       mux->clientsocket :
-	       mux->symonsocket);
-    maxsock++;
-
-    for (;;) { /* FOREVER - until a valid symon packet is received */
+    for (;;) {			/* FOREVER - until a valid symon packet is
+				 * received */
 	FD_ZERO(&readset);
 	FD_ZERO(&readset);
 	FD_SET(mux->clientsocket, &readset);
 	FD_SET(mux->clientsocket, &readset);
-	FD_SET(mux->symonsocket, &readset);
-	
+
+	maxsock = mux->clientsocket;
+
+	for (i = 0; i < AF_MAX; i++) {
+	    if (mux->symonsocket[i] > 0) {
+		FD_SET(mux->symonsocket[i], &readset);
+		maxsock = ((maxsock < mux->symonsocket[i]) ? mux->symonsocket[i] :
+			   maxsock);
+	    }
+	}
+
+	maxsock++;
 	socksactive = select(maxsock, &readset, NULL, NULL, NULL);
 	socksactive = select(maxsock, &readset, NULL, NULL, NULL);
-	
+
 	if (socksactive != -1) {
 	if (socksactive != -1) {
 	    if (FD_ISSET(mux->clientsocket, &readset)) {
 	    if (FD_ISSET(mux->clientsocket, &readset)) {
 		spawn_client(mux->clientsocket);
 		spawn_client(mux->clientsocket);
 	    }
 	    }
 
 
-	    if (FD_ISSET(mux->symonsocket, &readset)) {
-		if (recvsymonpacket(mux, sourcelist, source, packet))
-		    return;
-	    }
-	} else {
+	    for (i = 0; i < AF_MAX; i++)
+		if (FD_ISSET(mux->symonsocket[i], &readset)) {
+		    if (recv_symon_packet(mux, i, source, packet))
+			return;
+		}
+	}
+	else {
 	    if (errno == EINTR)
 	    if (errno == EINTR)
-		return;  /* signal received while waiting, bail out */
+		return;		/* signal received while waiting, bail out */
 	}
 	}
     }
     }
 }
 }
 /* Receive a symon packet for mux. Checks if the source is allowed and returns the source found.
 /* Receive a symon packet for mux. Checks if the source is allowed and returns the source found.
- * return 0 if no valid packet found 
+ * return 0 if no valid packet found
  */
  */
-int
-recvsymonpacket(struct mux *mux, struct sourcelist *sourcelist, 
-	      struct source **source, struct symonpacket *packet) 
-
+int 
+recv_symon_packet(struct mux * mux, int socknr, struct source ** source,
+		  struct symonpacket * packet)
 {
 {
-    struct sockaddr_in sind;
-    u_int32_t sourceaddr;
-    int size;
-    unsigned int received;
+    char hbuf[NI_MAXHOST], sbuf[NI_MAXSERV];
+    struct sockaddr_storage sind;
     socklen_t sl;
     socklen_t sl;
-    int tries;
+    int size, tries;
+    unsigned int received;
     u_int32_t crc;
     u_int32_t crc;
 
 
     received = 0;
     received = 0;
     tries = 0;
     tries = 0;
+    bzero((void *) hbuf, sizeof(hbuf));
+    bzero((void *) sbuf, sizeof(sbuf));
+
     do {
     do {
 	sl = sizeof(sind);
 	sl = sizeof(sind);
 
 
-	size = recvfrom(mux->symonsocket, (void *)packet->data + received, 
-			sizeof(struct symonpacket) - received, 
-			0, (struct sockaddr *)&sind, &sl);
+	size = recvfrom(mux->symonsocket[socknr], (void *) packet->data + received,
+			sizeof(struct symonpacket) - received,
+			0, (struct sockaddr *) & sind, &sl);
 	if (size > 0)
 	if (size > 0)
-	  received += size;
+	    received += size;
 
 
 	tries++;
 	tries++;
-    } while ((size == -1) && 
-	     (errno == EAGAIN || errno == EINTR) && 
+    } while ((size == -1) &&
+	     (errno == EAGAIN || errno == EINTR) &&
 	     (tries < SYMUX_MAXREADTRIES) &&
 	     (tries < SYMUX_MAXREADTRIES) &&
 	     (received < sizeof(packet->data)));
 	     (received < sizeof(packet->data)));
 
 
-    if ((size == -1) && 
-	errno) 
-      warning("recvfrom failed: %.200s", strerror(errno));
+    if ((size == -1) &&
+	errno)
+	warning("recvfrom failed: %.200s", strerror(errno));
+
+    *source = find_source_sockaddr(&mux->sol, (struct sockaddr *) & sind);
 
 
-    sourceaddr = ntohl((u_int32_t)sind.sin_addr.s_addr);
-    *source = find_source_ip(sourcelist, sourceaddr);
-	    
     if (*source == NULL) {
     if (*source == NULL) {
-	debug("ignored data from %u.%u.%u.%u",
-	      IPAS4BYTES(sourceaddr));
+	getnameinfo((struct sockaddr *) & sind, sind.ss_len, hbuf, sizeof(hbuf),
+		    sbuf, sizeof(sbuf), NI_NUMERICHOST | NI_NUMERICSERV);
+	debug("ignored data from %s:%s", hbuf, sbuf);
 	return 0;
 	return 0;
-    } else {
+    }
+    else {
 	/* get header stream */
 	/* get header stream */
 	mux->offset = getheader(packet->data, &packet->header);
 	mux->offset = getheader(packet->data, &packet->header);
 	/* check crc */
 	/* check crc */
@@ -195,39 +242,52 @@ recvsymonpacket(struct mux *mux, struct sourcelist *sourcelist,
 	packet->header.crc = 0;
 	packet->header.crc = 0;
 	setheader(packet->data, &packet->header);
 	setheader(packet->data, &packet->header);
 	crc ^= crc32(packet->data, received);
 	crc ^= crc32(packet->data, received);
-	if ( crc != 0 ) {
-	    warning("ignored packet with bad crc from %u.%u.%u.%u",
-		    IPAS4BYTES(sourceaddr));
+	if (crc != 0) {
+	    getnameinfo((struct sockaddr *) & sind, sind.ss_len, hbuf, sizeof(hbuf),
+			sbuf, sizeof(sbuf), NI_NUMERICHOST | NI_NUMERICSERV);
+	    warning("ignored packet with bad crc from %s:%s",
+		    hbuf, sbuf);
 	    return 0;
 	    return 0;
 	}
 	}
 	/* check packet version */
 	/* check packet version */
 	if (packet->header.symon_version != SYMON_PACKET_VER) {
 	if (packet->header.symon_version != SYMON_PACKET_VER) {
-	    warning("ignored packet with wrong version %d", 
-		    packet->header.symon_version);
+	    getnameinfo((struct sockaddr *) & sind, sind.ss_len, hbuf, sizeof(hbuf),
+			sbuf, sizeof(sbuf), NI_NUMERICHOST | NI_NUMERICSERV);
+	    warning("ignored packet with wrong version %d from %s:%s",
+		    packet->header.symon_version, hbuf, sbuf);
 	    return 0;
 	    return 0;
-	} else {
-	    if (flag_debug) 
-		debug("good data received from %u.%u.%u.%u",
-		      IPAS4BYTES(sourceaddr));
-	    return 1;  /* good packet received */
-	} 
+	}
+	else {
+	    if (flag_debug) {
+		getnameinfo((struct sockaddr *) & sind, sind.ss_len, hbuf, sizeof(hbuf),
+		       sbuf, sizeof(sbuf), NI_NUMERICHOST | NI_NUMERICSERV);
+		debug("good data received from %s:%s", hbuf, sbuf);
+	    }
+	    return 1;		/* good packet received */
+	}
     }
     }
 }
 }
 int 
 int 
-acceptconnection(int sock)
+accept_connection(int sock, char *peername, int peernamesize)
 {
 {
-    struct sockaddr_in sind;
+    char hbuf[NI_MAXHOST], sbuf[NI_MAXSERV];
+    struct sockaddr_storage sind;
     socklen_t len;
     socklen_t len;
-    u_int32_t clientaddr;
     int clientsock;
     int clientsock;
 
 
-    if ((clientsock = accept(sock, (struct sockaddr *)&sind, &len)) < 0)
-	fatal("Failed to accept an incoming connection. (.200%s)",
+    bzero((void *) hbuf, sizeof(hbuf));
+    bzero((void *) sbuf, sizeof(sbuf));
+
+    if ((clientsock = accept(sock, (struct sockaddr *) & sind, &len)) < 0)
+	fatal("failed to accept an incoming connection. (.200%s)",
 	      strerror(errno));
 	      strerror(errno));
 
 
-    clientaddr = ntohl((u_int32_t)sind.sin_addr.s_addr);
-    info("Accepted incoming client connection from %u.%u.%u.%u",
-	 IPAS4BYTES(clientaddr));
+
+    if (getnameinfo((struct sockaddr *) & sind, sind.ss_len, hbuf, sizeof(hbuf),
+		    sbuf, sizeof(sbuf), NI_NUMERICHOST | NI_NUMERICSERV))
+	snprintf(peername, peernamesize, "<unknown>");
+    else
+	snprintf(peername, peernamesize, "%s:%s", hbuf, sbuf);
 
 
     return clientsock;
     return clientsock;
-}   
+}

+ 7 - 11
symon/symux/symuxnet.h

@@ -1,4 +1,4 @@
-/* $Id: symuxnet.h,v 1.6 2002/09/14 15:54:56 dijkstra Exp $ */
+/* $Id: symuxnet.h,v 1.8 2002/11/29 10:45:22 dijkstra Exp $ */
 
 
 /*
 /*
  * Copyright (c) 2001-2002 Willem Dijkstra
  * Copyright (c) 2001-2002 Willem Dijkstra
@@ -37,14 +37,10 @@
 
 
 /* prototypes */
 /* prototypes */
 __BEGIN_DECLS
 __BEGIN_DECLS
-int  acceptconnection(int);
-int  getsymonsocket(struct mux *);
-int  getclientsocket(struct mux *);
-void waitfortraffic(struct mux *, struct sourcelist *, 
-		    struct source **, struct symonpacket *);
-int  recvsymonpacket(struct mux *, struct sourcelist *, 
-		   struct source **, struct symonpacket *);
-int  check_crc_packet(struct symonpacket *);
+int get_client_socket(struct mux *);
+int get_symon_sockets(struct mux *);
+int accept_connection(int, char *, int);
+int recv_symon_packet(struct mux *, int, struct source **, struct symonpacket *);
+void wait_for_traffic(struct mux *, struct source **, struct symonpacket *);
 __END_DECLS
 __END_DECLS
-#endif /*_SYMUX_SYMUXNET_H*/
-
+#endif				/* _SYMUX_SYMUXNET_H */