Max has uploaded this change for review. ( https://gerrit.osmocom.org/11885


Change subject: Add OpenVPN status helper from corresponding ticket
......................................................................

Add OpenVPN status helper from corresponding ticket

Change-Id: I912d943cdc7024e3ddd92e0a122ac2dd4fbf0a18
Related: SYS#2655
---
A contrib/openvpn-status-export.pl
1 file changed, 136 insertions(+), 0 deletions(-)



  git pull ssh://gerrit.osmocom.org:29418/osmo-sysmon refs/changes/85/11885/1

diff --git a/contrib/openvpn-status-export.pl b/contrib/openvpn-status-export.pl
new file mode 100755
index 0000000..cc2c6f2
--- /dev/null
+++ b/contrib/openvpn-status-export.pl
@@ -0,0 +1,136 @@
+#!/usr/bin/perl -w
+use strict;
+
+# Script to export the OpenVPN daemon status information (which clients
+# are connected from where) as a JSON file that can be served via HTTP.
+#
+# (C) 2015 by sysmocom - s.f.m.c. GmbH, All rights reserved.
+# Author: Harald Welte
+
+use JSON;
+use Linux::Inotify2;
+use Net::Netmask;
+
+my $OPENVPN_STATE_FILE = "/var/tmp/openvpn.status";
+my $JSON_OUTPUT_FILE = "/var/www/openvpn/status.json";
+
+my $srcip_table = {
+       'Iridium' => [
+               '172.28.204.0/23',
+               ],
+       'Kabel Deutschland' => [
+               '91.64.0.0/16', '91.65.0.0/16', '91.66.0.0/16', '91.67.0.0/16',
+               ],
+       'Scarlet' => [
+               '213.49.64.0/18',
+               ],
+       'hmw-consulting' => [
+               '83.236.178.200/29',
+               ],
+       'Hetzner' => [
+               '144.76.0.0/16', '5.9.81.32/27',
+               ],
+       'Skynet' => [
+               '91.183.84.0/22', '81.243.248.0/22',
+               ],
+};
+
+my %netblocks;
+
+sub read_netmask_table($)
+{
+       my ($t) = @_;
+
+       foreach my $k (keys %$t) {
+               my $table = {};
+               foreach my $net (@{$$t{$k}}) {
+                       my $block = new Net::Netmask($net);
+                       $block->storeNetblock($table);
+               }
+               $netblocks{$k} = $table;
+       }
+}
+
+sub classify_srcip($)
+{
+       my ($ip) = @_;
+       foreach my $k (%netblocks) {
+               my $block = findNetblock($ip, $netblocks{$k});
+               if ($block) {
+                       return $k;
+               }
+       }
+       return undef;
+}
+
+# read the openvpn.status file and parse it, return hash reference to
+# its contents.
+sub get_openvpn_clients($)
+{
+       my ($fname) = @_;
+       my $state = 'init';
+       my $href;
+       my @clients;
+
+       $$href{version} = 1;
+
+       open(INFILE, "<", $fname);
+       while (my $line = <INFILE>) {
+               chomp($line);
+               if ($line =~ /^OpenVPN CLIENT LIST$/) {
+                       $state = 'client_list';
+               } elsif ($line =~ /^ROUTING\ TABLE$/) {
+                       $state = 'routing_table';
+               } else {
+                       if ($state eq 'client_list') {
+                               my %cl;
+                               if ($line =~ /^Updated,(.*)/) {
+                                       $$href{updated} = $1;
+                               } elsif ($line =~ 
/^(\S+),([0-9\.]+)\:(\d+),(\d+),(\d+),(.*)$/) {
+                                       $cl{name} = $1;
+                                       $cl{srcip} = $2;
+                                       $cl{operator} = classify_srcip($2);
+                                       $cl{srcport} = $3 + 0;
+                                       $cl{bytes_rx} = $4 + 0;
+                                       $cl{bytes_tx} = $5 + 0;
+                                       $cl{connected_since} = $6;
+                                       push(@clients, \%cl);
+                               }
+                       }
+               }
+       }
+       close(INFILE);
+
+       $$href{clients} = \@clients;
+
+       return $href;
+}
+
+# inotify handler to re-parse/convert openvpn.status on any change
+sub status_in_handler
+{
+       my $e = shift;
+
+       # read/parse openvpn.status
+       my $cl = get_openvpn_clients($e->fullname);
+
+       # write result to file
+       open(OUTFILE, ">", $JSON_OUTPUT_FILE);
+       print(OUTFILE to_json($cl, { pretty => 1 }));
+       close(OUTFILE);
+
+       # also print it to console for debugging
+       print(to_json($cl, { pretty => 1 }));
+}
+
+
+
+# main
+
+read_netmask_table($srcip_table);
+
+my $inotify = new Linux::Inotify2 or die("Can't create inotify object: $!");
+$inotify->watch($OPENVPN_STATE_FILE, IN_MODIFY, \&status_in_handler);
+
+# endless loop, wait for inotify enents
+1 while $inotify->poll;

--
To view, visit https://gerrit.osmocom.org/11885
To unsubscribe, or for help writing mail filters, visit 
https://gerrit.osmocom.org/settings

Gerrit-Project: osmo-sysmon
Gerrit-Branch: master
Gerrit-MessageType: newchange
Gerrit-Change-Id: I912d943cdc7024e3ddd92e0a122ac2dd4fbf0a18
Gerrit-Change-Number: 11885
Gerrit-PatchSet: 1
Gerrit-Owner: Max <msur...@sysmocom.de>

Reply via email to