[prev in list] [next in list] [prev in thread] [next in thread] 

List:       ipcop-svn
Subject:    [Ipcop-svn] SF.net SVN: ipcop:[1620] ipcop/trunk
From:       owes () users ! sourceforge ! net
Date:       2008-07-31 20:20:00
Message-ID: E1KOecy-000726-PW () d5vjzd1 ! ch3 ! sourceforge ! com
[Download RAW message or body]

Revision: 1620
          http://ipcop.svn.sourceforge.net/ipcop/?rev=1620&view=rev
Author:   owes
Date:     2008-07-31 20:19:58 +0000 (Thu, 31 Jul 2008)

Log Message:
-----------
Use XML output from connection tracking.
connections.cgi now shows traffic (packets and bytes) or status (1.4 style info).

Modified Paths:
--------------
    ipcop/trunk/doc/Configuration-Files
    ipcop/trunk/html/cgi-bin/connections.cgi
    ipcop/trunk/src/misc-progs/conntrack_helper.c

Modified: ipcop/trunk/doc/Configuration-Files
===================================================================
--- ipcop/trunk/doc/Configuration-Files	2008-07-31 16:17:03 UTC (rev 1619)
+++ ipcop/trunk/doc/Configuration-Files	2008-07-31 20:19:58 UTC (rev 1620)
@@ -16,6 +16,7 @@
         KEYMAP                      used keyboard map, for example \
/usr/share/kbd/keymaps/i386/qwertz/de.map.gz  LANGUAGE                    short \
                language name, for example de
         TIMEZONE                    used timezone, for example \
/usr/share/zoneinfo/posix/Europe/Berlin +	DISPLAY_CONNECTIONS         display style \
for connections.cgi, TRAFFIC or STATUS  
 ================================================================================
 

Modified: ipcop/trunk/html/cgi-bin/connections.cgi
===================================================================
--- ipcop/trunk/html/cgi-bin/connections.cgi	2008-07-31 16:17:03 UTC (rev 1619)
+++ ipcop/trunk/html/cgi-bin/connections.cgi	2008-07-31 20:19:58 UTC (rev 1620)
@@ -22,6 +22,8 @@
 #
 # (c) 2006 Franck - add sorting+filtering capability
 #
+# (c) 2008 Olaf for the IPCop team - use conntrack with XML output from \
conntrack-tools +#
 # $Id$
 #
 
@@ -32,30 +34,42 @@
 my @routes=();
 my @colour=();
 
-use Net::IPv4Addr qw( :all );
-
 use strict;
 
 # enable only the following on debugging purpose
-#use warnings;
-#use CGI::Carp 'fatalsToBrowser';
+use warnings; no warnings 'once';
+use CGI::Carp 'fatalsToBrowser';
 
+use Net::IPv4Addr qw( :all );
+use XML::Simple;
+use XML::Parser::Style::Tree;
+
 require '/var/ipcop/general-functions.pl';
 require '/var/ipcop/lang.pl';
 require '/var/ipcop/header.pl';
 
-#workaround to suppress a warning when a variable is used only once
-my @dummy = ( ${Header::table1colour} );
-undef (@dummy);
-
 my $icount = 0;
 # Read various files
 
 my %netsettings=();
 &General::readhash('/var/ipcop/ethernet/settings', \%netsettings);
+my %mainsettings=();
+$mainsettings{'DISPLAY_CONNECTIONS'} = 'TRAFFIC';
+&General::readhash('/var/ipcop/main/settings',\%mainsettings);
+my %cgiparams=();
+$cgiparams{'ACTION'} = '';
+&General::getcgihash(\%cgiparams);
 
+# Fetch connection tracking info in XML format
 my @active = `/usr/local/bin/conntrack_helper`;
 
+
+if ( $cgiparams{'ACTION'} eq 'SAVE' ) {
+	$mainsettings{'DISPLAY_CONNECTIONS'} = $cgiparams{'DISPLAY_CONNECTIONS'};
+	&General::writehash('/var/ipcop/main/settings', \%mainsettings);
+}
+
+
 my $aliasfile = '/var/ipcop/ethernet/aliases';
 open(ALIASES, $aliasfile) or die 'Unable to open aliases file.';
 my @aliases = <ALIASES>;
@@ -184,12 +198,16 @@
 $cgiparams{'SEE_SORT'} = '';
 &General::getcgihash(\%cgiparams);
 
+&Header::showhttpheaders();
+&Header::openpage($Lang::tr{'connections'}, 1, '');
+&Header::openbigbox('100%', 'left');
+
 my @list_proto = ($Lang::tr{'all'}, 'icmp', 'udp', 'tcp');
 my @list_state = ($Lang::tr{'all'}, 'SYN_SENT', 'SYN_RECV', 'ESTABLISHED', \
'FIN_WAIT',  'CLOSE_WAIT', 'LAST_ACK', 'TIME_WAIT', 'CLOSE', 'LISTEN');
 my @list_mark = ($Lang::tr{'all'}, '[ASSURED]', '[UNREPLIED]');
 my @list_sort = ('orgsip','protocol', 'expires', 'status', 'orgdip', 'orgsp',
-		    'orgdp', 'exsip', 'exdip', 'exsp', 'exdp', 'marked');
+		    'orgdp', 'repsip', 'repdip', 'repsp', 'repdp', 'marked');
 
 # init or silently correct unknown value...
 if ( ! grep ( /^$cgiparams{'SEE_PROTO'}$/ , @list_proto )) { $cgiparams{'SEE_PROTO'} \
= $list_proto[0] }; @@ -208,107 +226,59 @@
 my $unknownlines = '';	# should be empty all the time...
 my $index = 0;		# just a counter to make unique entryies in entries
 
-foreach my $line (@active) {
-	my $protocol='';
-	my $expires='';
-	my $status='';
-	my $orgsip='';
-	my $orgdip='';
-	my $orgsp='';
-	my $orgdp='';
-	my $exsip='';
-	my $exdip='';
-	my $exsp='';
-	my $exdp='';
-	my $marked='';
-	my $use='';
-	my $extraline='';
-
+foreach my $line (@active) 
+{
 	chomp($line);
-	my @temp = split(' ',$line);
+	my $xml = new XML::Simple;
+	my $data = $xml->XMLin($line);
 
-
-	if ( ($temp[0] eq 'ipv4') && ($temp[2] eq 'udp') ) {
-		my $offset = 0;
-		$marked = '';
-		$protocol = $temp[2];
-		$expires = $temp[4];
-		$status = ' ';
-		$orgsip = substr $temp[5], 4;
-		$orgdip = substr $temp[6], 4;
-		$orgsp = substr $temp[7], 6;
-		$orgdp = substr $temp[8], 6;
-		if ($temp[11] eq '[UNREPLIED]') {
-			$offset = 1;
-			$marked = $temp[11];
-			$use = substr $temp[19], 4;
-		} else {
-		    if ((substr $temp[17], 0, 3) eq 'use' ) {
-			$marked = '';
-			$use = substr $temp[17], 4;
-		    } else {
-		       	$marked = $temp[17];
-			$use = substr $temp[18], 4;
-		    }
+	foreach my $elt ( @{$data->{meta}} )
+	{
+		if ( $elt->{direction} eq 'original' )
+		{
+			$entries{$index}->{protocol} = $elt->{layer4}->{protoname};
+			$entries{$index}->{orgsip}   = $elt->{layer3}->{src};
+			$entries{$index}->{orgdip}   = $elt->{layer3}->{dst};
+			$entries{$index}->{orgsp}    = $elt->{layer4}->{sport};
+			$entries{$index}->{orgdp}    = $elt->{layer4}->{dport};
+			$entries{$index}->{orgtraf}  = $elt->{counters}->{packets}." / \
".$elt->{counters}->{bytes};  }
-		$exsip = substr $temp[11 + $offset], 4;
-		$exdip = substr $temp[12 + $offset], 4;
-		$exsp = substr $temp[13 + $offset], 6;
-		$exdp = substr $temp[14 + $offset], 6;
-
-		$extraline = "$temp[9] $temp[10] , $temp[15+$offset] $temp[16+$offset]";
-	}
-	elsif ( ($temp[0] eq 'ipv4') && ($temp[2] eq 'tcp') ) {
-		my $offset = 0;
-		$protocol = $temp[2];
-		$expires = $temp[4];
-		$status = $temp[5];
-		$orgsip = substr $temp[6], 4;
-		$orgdip = substr $temp[7], 4;
-		$orgsp = substr $temp[8], 6;
-		$orgdp = substr $temp[9], 6;
-		if ($temp[12] eq '[UNREPLIED]') {
-			$marked = $temp[0];
-			$offset = 1;
-		} else {
-			$marked = $temp[18];
+		elsif ( $elt->{direction} eq 'reply' )
+		{
+			$entries{$index}->{repsip}    = $elt->{layer3}->{src};
+			$entries{$index}->{repdip}    = $elt->{layer3}->{dst};
+			$entries{$index}->{repsp}     = $elt->{layer4}->{sport};
+			$entries{$index}->{repdp}     = $elt->{layer4}->{dport};
+			$entries{$index}->{reptraf}   = $elt->{counters}->{packets}." / \
".$elt->{counters}->{bytes};  }
-		$exsip = substr $temp[12 + $offset], 4;
-		$exdip = substr $temp[13 + $offset], 4;
-		$exsp = substr $temp[14 + $offset], 6;
-		$exdp = substr $temp[15 + $offset], 6;
-		$use = substr $temp[20], 4;
-
-		$extraline = "$temp[10] $temp[11] , $temp[16+$offset] $temp[17+$offset]";
+		elsif ( $elt->{direction} eq 'independent' )
+		{
+			for my $key ( keys %{$elt} )
+			{
+				if ( $key eq 'timeout' )
+				{
+					$entries{$index}->{expires} = ${$elt}{$key};
+				}
+				elsif ( $key eq 'mark' )
+				{
+					$entries{$index}->{marked}  = ${$elt}{$key};
+				}
+				elsif ( $key eq 'use' )
+				{
+					$entries{$index}->{use}     = ${$elt}{$key};
+				}
+				elsif ( ($key eq 'id') || ($key eq 'direction') )
+				{
+				}
+				else
+				{
+					$entries{$index}->{status}  = $key;
+				}
+			}
+		}
 	}
 
-	# Only from this point, lines have the same known format/field
-	# The floating fields [UNREPLIED] [ASSURED] etc are ok.
-
-	# Store the line in a hash array for sorting
-	if ( $protocol ) { # line is decoded ?
-		my @record = (  'index', $index++,
-			'extra', $extraline,
-			    'protocol', $protocol,
-			    'expires',  $expires,
-			    'status',   $status,
-			    'orgsip',   $orgsip,
-			    'orgdip',   $orgdip,
-			    'orgsp',    $orgsp,
-			    'orgdp',    $orgdp,
-			    'exsip',    $exsip,
-			    'exdip', 	$exdip,
-			    'exsp',	$exsp,
-			    'exdp',	$exdp,
-			    'marked',	$marked,
-			    'use',	$use);
-		my $record = {};                        	# create a reference to empty hash
-		%{$record} = @record;                	# populate that hash with @record
-		$entries{$record->{index}} = $record; 	# add this to a hash of hashes
-	} else { # it was not a known line
-		$unknownlines .= "<tr bgcolor='${Header::table1colour}'>";
-		$unknownlines .= "<td colspan='9'> unknown:$line</td></tr>";
-	}
+	$index++;
 }
 
 # Build listbox objects
@@ -319,33 +289,90 @@
 my $menu_mark  = &make_select ('SEE_MARK',  $cgiparams{'SEE_MARK'},  @list_mark);
 my $menu_sort  = &make_select ('SEE_SORT',  $cgiparams{'SEE_SORT'},  @list_sort);
 
-&Header::showhttpheaders();
-&Header::openpage($Lang::tr{'connections'}, 1, '');
-&Header::openbigbox('100%', 'left');
 &Header::openbox('100%', 'left', $Lang::tr{'connection tracking'});
 
+my %selected = ();
+$selected{'TRAFFIC'} = '';
+$selected{'STATUS'}  = '';
+$selected{$mainsettings{'DISPLAY_CONNECTIONS'}} = "selected='selected'";
+
 print <<END
 <form method='post' action='$ENV{'SCRIPT_NAME'}'>
-<table width='60%'>
-<tr><td align='center'><b>$Lang::tr{'legend'} : </b></td>
-    <td align='center' class='ipcop_iface_bg_green'><b>$Lang::tr{'lan'}</b></td>
-    <td align='center' class='ipcop_iface_bg_red'><b>$Lang::tr{'internet'}</b></td>
-    <td align='center' class='ipcop_iface_bg_blue'><b>$Lang::tr{'wireless'}</b></td>
-    <td align='center' class='ipcop_iface_bg_orange'><b>$Lang::tr{'dmz'}</b></td>
-    <td align='center' class='ipcop_iface_bg_fw'><b>IPCop</b></td>
-    <td align='center' class='ipcop_iface_bg_ipsec'><b>IPsec</b></td>
-    <td align='center' class='ipcop_iface_bg_ovpn'><b>OpenVPN</b></td>
+<table width='100%'><tr>
+	<td width='25%' class='base'>$Lang::tr{'display'}:</td>
+	<td width='25%'><select name='DISPLAY_CONNECTIONS'><option value='TRAFFIC' \
$selected{'TRAFFIC'}>$Lang::tr{'traffic'}</option><option value='STATUS' \
$selected{'STATUS'}>$Lang::tr{'status'}</option></select></td> +	<td \
width='25%'>&nbsp;</td> +	<td width='25%'>&nbsp;</td>
+</tr></table><table width='100%'><tr>
+	<td class='base' width='55%'>&nbsp;</td>
+	<td width='40%' align='center'><input type='hidden' name='ACTION' value='SAVE' \
/><input type='submit' name='SUBMIT' value='$Lang::tr{'save'}' /></td> +	<td \
width='5%' align='right'> +		<a \
href='${General::adminmanualurl}/status.html#connections' target='_blank'> +		<img \
src='/images/web-support.png' alt='$Lang::tr{'online help en'}' \
title='$Lang::tr{'online help en'}' /></a></td> +</tr></table>
+</form>
+<hr />
+END
+;
+
+
+if ( $mainsettings{'DISPLAY_CONNECTIONS'} eq 'TRAFFIC' )
+{
+print <<END
+<table cellpadding='2'>
+<tr><td align='center'><b>$Lang::tr{'protocol'}</b></td>
+    <td align='center'><b>$Lang::tr{'original'}<br />$Lang::tr{'source ip and \
port'}</b></td> +    <td align='center'><b>$Lang::tr{'original'}<br />$Lang::tr{'dest \
ip and port'}</b></td> +	<td align='center'><b>$Lang::tr{'packets'} / \
$Lang::tr{'bytes'}</b></td> +    <td align='center'><b>$Lang::tr{'reply'}<br \
/>$Lang::tr{'source ip and port'}</b></td> +    <td \
align='center'><b>$Lang::tr{'reply'}<br />$Lang::tr{'dest ip and port'}</b></td> \
+	<td align='center'><b>$Lang::tr{'packets'} / $Lang::tr{'bytes'}</b></td>  </tr>
-</table>
-<br />
+END
+;
+
+foreach my $entry (sort sort_entries keys %entries) {
+	my $orgsipcolour = &ipcolour( $entries{$entry}->{orgsip} );
+	my $orgdipcolour = &ipcolour( $entries{$entry}->{orgdip} );
+	my $repsipcolour  = &ipcolour( $entries{$entry}->{repsip} );
+	my $repdipcolour  = &ipcolour( $entries{$entry}->{repdip} );
+	print <<END
+	<tr class='table1colour'>
+	<td align='center'>$entries{$entry}->{protocol}</td>
+	<td align='center' class='$orgsipcolour'>
+	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{orgsip}' \
class='$orgsipcolour'> +	    $entries{$entry}->{orgsip}
+	    </a>:$entries{$entry}->{orgsp}</td>
+	<td align='center' class='$orgdipcolour'>
+	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{orgdip}' \
class='$orgdipcolour'> +	    $entries{$entry}->{orgdip}
+	    </a>:$entries{$entry}->{orgdp}</td>
+		<td align='center'>$entries{$entry}->{orgtraf}</td>
+	<td align='center' class='$repsipcolour'>
+	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{repsip}' \
class='$repsipcolour'> +	    $entries{$entry}->{repsip}
+	    </a>:$entries{$entry}->{repsp}</td>
+	<td align='center' class='$repdipcolour'>
+	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{repdip}' \
class='$repdipcolour'> +	    $entries{$entry}->{repdip}
+	    </a>:$entries{$entry}->{repdp}</td>
+	<td align='center'>$entries{$entry}->{reptraf}</td>
+	</tr>
+END
+;
+}
+}
+else
+{
+print <<END
 <table cellpadding='2'>
 <tr><td align='center'><b>$Lang::tr{'protocol'}</b></td>
+    <td align='center'><b>$Lang::tr{'original'}<br />$Lang::tr{'source ip and \
port'}</b></td> +    <td align='center'><b>$Lang::tr{'original'}<br />$Lang::tr{'dest \
ip and port'}</b></td> +    <td align='center'><b>$Lang::tr{'reply'}<br \
/>$Lang::tr{'source ip and port'}</b></td> +    <td \
                align='center'><b>$Lang::tr{'reply'}<br />$Lang::tr{'dest ip and \
                port'}</b></td>
     <td align='center'><b>$Lang::tr{'expires'}<br />($Lang::tr{'seconds'})</b></td>
     <td align='center'><b>$Lang::tr{'connection'}<br />$Lang::tr{'status'}</b></td>
-    <td align='center'><b>$Lang::tr{'original'}<br />$Lang::tr{'source ip and \
                port'}</b></td>
-    <td align='center'><b>$Lang::tr{'original'}<br />$Lang::tr{'dest ip and \
                port'}</b></td>
-    <td align='center'><b>$Lang::tr{'expected'}<br />$Lang::tr{'source ip and \
                port'}</b></td>
-    <td align='center'><b>$Lang::tr{'expected'}<br />$Lang::tr{'dest ip and \
port'}</b></td>  <td align='center'><b>$Lang::tr{'marked'}</b></td>
     <td align='center'><b>$Lang::tr{'use'}</b></td>
 </tr>
@@ -355,13 +382,11 @@
 foreach my $entry (sort sort_entries keys %entries) {
 	my $orgsipcolour = &ipcolour( $entries{$entry}->{orgsip} );
 	my $orgdipcolour = &ipcolour( $entries{$entry}->{orgdip} );
-	my $exsipcolour  = &ipcolour( $entries{$entry}->{exsip} );
-	my $exdipcolour  = &ipcolour( $entries{$entry}->{exdip} );
+	my $repsipcolour  = &ipcolour( $entries{$entry}->{repsip} );
+	my $repdipcolour  = &ipcolour( $entries{$entry}->{repdip} );
 	print <<END
 	<tr class='table1colour'>
 	<td align='center'>$entries{$entry}->{protocol}</td>
-	<td align='center'>$entries{$entry}->{expires}</td>
-	<td align='center'>$entries{$entry}->{status}</td>
 	<td align='center' class='$orgsipcolour'>
 	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{orgsip}' \
class='$orgsipcolour'>  $entries{$entry}->{orgsip}
@@ -370,26 +395,39 @@
 	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{orgdip}' \
class='$orgdipcolour'>  $entries{$entry}->{orgdip}
 	    </a>:$entries{$entry}->{orgdp}</td>
-	<td align='center' class='$exsipcolour'>
-	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{exsip}' \
                class='$exsipcolour'>
-	    $entries{$entry}->{exsip}
-	    </a>:$entries{$entry}->{exsp}</td>
-	<td align='center' class='$exdipcolour'>
-	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{exdip}' \
                class='$exdipcolour'>
-	    $entries{$entry}->{exdip}
-	    </a>:$entries{$entry}->{exdp}</td>
+	<td align='center' class='$repsipcolour'>
+	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{repsip}' \
class='$repsipcolour'> +	    $entries{$entry}->{repsip}
+	    </a>:$entries{$entry}->{repsp}</td>
+	<td align='center' class='$repdipcolour'>
+	    <a href='/cgi-bin/ipinfo.cgi?ip=$entries{$entry}->{repdip}' \
class='$repdipcolour'> +	    $entries{$entry}->{repdip}
+	    </a>:$entries{$entry}->{repdp}</td>
+	<td align='center'>$entries{$entry}->{expires}</td>
+	<td align='center'>$entries{$entry}->{status}</td>
 	<td align='center'>$entries{$entry}->{marked}</td>
 	<td align='center'>$entries{$entry}->{use}</td>
 	</tr>
 END
 ;
-		if ( $entries{$entry}->{extra} ne '' ) 
-		{
-			print "<tr><td  colspan='9'>$entries{$entry}->{extra}</td></tr>";
-		}
 }
+}
 
-print "$unknownlines</table></form>";
+print <<END
+</table>
+<hr />
+<table width='60%'><tr>
+	<td align='center'><b>$Lang::tr{'legend'}: </b></td>
+    <td align='center' class='ipcop_iface_bg_green'><b>$Lang::tr{'lan'}</b></td>
+    <td align='center' class='ipcop_iface_bg_red'><b>$Lang::tr{'internet'}</b></td>
+    <td align='center' class='ipcop_iface_bg_blue'><b>$Lang::tr{'wireless'}</b></td>
+    <td align='center' class='ipcop_iface_bg_orange'><b>$Lang::tr{'dmz'}</b></td>
+    <td align='center' class='ipcop_iface_bg_fw'><b>IPCop</b></td>
+    <td align='center' class='ipcop_iface_bg_ipsec'><b>IPsec</b></td>
+    <td align='center' class='ipcop_iface_bg_ovpn'><b>OpenVPN</b></td>
+</tr></table>
+END
+;
 
 &Header::closebox();
 &Header::closebigbox();
@@ -413,7 +451,7 @@
 # param1: name
 # param2: current value selected
 # param3: field list
-sub make_select ($,$,$) {
+sub make_select () {
 	my $select_name = shift;
 	my $selected    = shift;
 	my $select = "<select name='$select_name'>";
@@ -445,14 +483,14 @@
 # Used to sort the table containing the lines displayed.
 sub sort_entries { #Reverse is not implemented
 	my $qs=$cgiparams{'SEE_SORT'};
-	if ($qs =~ /orgsip|orgdip|exsip|exdip/) {
+	if ($qs =~ /orgsip|orgdip|repsip|repdip/) {
 		my @a = split(/\./,$entries{$a}->{$qs});
 		my @b = split(/\./,$entries{$b}->{$qs});
 		($a[0]<=>$b[0]) ||
 		($a[1]<=>$b[1]) ||
 		($a[2]<=>$b[2]) ||
 		($a[3]<=>$b[3]);
-	} elsif ($qs =~ /expire|orgsp|orgdp|exsp|exdp/) {
+	} elsif ($qs =~ /expire|orgsp|orgdp|repsp|repdp/) {
 		$entries{$a}->{$qs} <=> $entries{$b}->{$qs};
 	} else {
 		$entries{$a}->{$qs} cmp $entries{$b}->{$qs};

Modified: ipcop/trunk/src/misc-progs/conntrack_helper.c
===================================================================
--- ipcop/trunk/src/misc-progs/conntrack_helper.c	2008-07-31 16:17:03 UTC (rev 1619)
+++ ipcop/trunk/src/misc-progs/conntrack_helper.c	2008-07-31 20:19:58 UTC (rev 1620)
@@ -29,7 +29,7 @@
   if ( !(initsetuid()) )
     exit(1);
 
-  safe_system("/usr/sbin/conntrack -L -o extended");
+  safe_system("/usr/sbin/conntrack -L -o xml 2>/dev/null");
 
   return(0);
 }


This was sent by the SourceForge.net collaborative development platform, the world's \
largest Open Source development site.

-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
_______________________________________________
Ipcop-svn mailing list
Ipcop-svn@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ipcop-svn


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic