On 21/9/2015 6:17 μμ, Jan Just Keijser wrote:

> Personally I'd use a simple file-based counter to figure out which 
> source IP address to use: 

I soon found out that we would need a slightly more sophisticated 
file-based counter (to record which public address is used or released 
and available, how many times a particular public address is used etc.)

So, I redesigned the whole process as follows, and I am already using 
it, seemingly without problems in the time being.

It uses a simple file (scr/list1) -a primitive database- to record how 
much a public address is currently (at any one time) used; Remember that 
our pool of public addresses is: 194.xxx.xxx.150-155. I have structured 
the file scr/list1 is as follows (fist col.: last octet of public addr 
pool - second col.: number of times currently used):

----------------------------------------------------------------
scr/list1 file
----------------------------------------------------------------

    150 0
    151 0
    152 0
    153 0
    154 0
    155 0

----------------------------------------------------------------

The logic is: Always keep the above file sorted (first on col2, then on 
col1) so as to have at the top the least used address (from lo to hi). 
When a client connects, give the first available address -always the one 
at the top- (here 150), increment 0 to 1 (and then sort the table). When 
a client disconnects, find its public address, decrement it by one (and 
sort the table). If all public addresses get used once, they will start 
getting used for a second time and so forth.

We also store a file /var/log/openvpn_client_$real_client_ip with the 
(last octet of the) public address assigned to the client, to read it 
back in the disconnect script.

----------------------------------------------------------------
client-connect script
----------------------------------------------------------------
#!/bin/bash

listfile="/etc/openvpn/scr/list1"
count=`awk 'NR==1 {print $2}' <$listfile`
ip=`awk 'NR==1 {print $1}' <$listfile`
count1=$((count+1))

sed -i "/$ip/{s/\ $count/\ $count1/}" $listfile
sort -k2,2 -k1 -o $listfile <$listfile

virtual_client_ip=$ifconfig_pool_remote_ip
real_client_ip=$trusted_ip

/sbin/iptables -t nat -A POSTROUTING -s "$virtual_client_ip" -j SNAT 
--to-source 194.xxx.xxx."$ip"

echo "$ip" > /var/log/openvpn_client_$real_client_ip

exit 0

----------------------------------------------------------------
client-disconnect script
----------------------------------------------------------------
#!/bin/bash
#

client_nat_scriptfile="/var/log/openvpn_client_$trusted_ip"

listfile="/etc/openvpn/scr/list1"

if [ -f $client_nat_scriptfile ]
then
    ip=`awk 'NR==1 {print $1}' <$client_nat_scriptfile`
    rm -f $client_nat_scriptfile
    /sbin/iptables -t nat -D POSTROUTING -s $ifconfig_pool_remote_ip -j 
SNAT --to-source 194.xxx.xxx.$ip
    count=`awk -v myip=$ip '$1==myip {print $2;exit;}' <$listfile`
    count1=$((count-1))
    sed -i "/$ip/{s/\ $count/\ $count1/}" $listfile
    sort -k2,2 -k1 -o $listfile <$listfile
fi

exit 0
----------------------------------------------------------------

At best, when we restart the server, a script should initialize the "db" 
in its zero state. (I have not done that, at least yet.) I guess the 
--up cmd would be the right place for such a script.

Any suggestions / improvements / additional ideas will be welcome.

Nick


------------------------------------------------------------------------------
_______________________________________________
Openvpn-users mailing list
Openvpn-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/openvpn-users

Reply via email to