Marcus wrote:
An authentication-script could look something like this:
#!/usr/bin/python
Not really able to help you with your python script, but this is a
really simple perl script I've written in the past (2005) for the same
purpose.
It uses a simple configuration file format:
radius_host=radius.example.com
radius_port=1812
radius_secret=foobar
It only does the AA part of RADIUS plus it supports Framed-IP-Address,
in case you need it. Be warned that the latter is implemented in a
rather hackish way.
IIRC, there are other solutions to RADIUS authentication that are more
featureful. Haven't evaluated them though, the above works pretty well
for me.
Regards,
Faidon
#!/usr/bin/perl
# OpenVPN auth-user-pass-verify script for RADIUS Authentication
#
# Copyright (c) 2005 Greek Research and Technology Network S.A.
#
# Author: Faidon Liambotis <parav...@debian.org>
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; version 2 dated June, 1991.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
use strict;
use warnings;
use POSIX;
use Authen::Radius;
### Configuration ###
my $conffn = '/etc/openvpn/radiuscnf';
### DO NOT EDIT ANYTHING BELOW THIS LINE ###
sysopen(CONFFILE, $conffn, O_RDONLY) or
die "Could not open configuration file: $conffn\n";
my %opt;
while (<CONFFILE>) {
chomp;
# Remove comments...
s/(\s|^)+#.*//;
# ...leading whitespace...
s/^\s+//;
# ...and trailing whitespace
s/\s+$//;
next unless length;
# foo = bar becomes $opt{foo} = bar
my ($var, $value) = split(/\s*=\s*/, $_, 2);
$opt{$var} = $value;
}
close (CONFFILE);
my $client_config_dir = $opt{clientdir} || '/etc/openvpn/clients/';
my $radius_dictionary = $opt{dictionary} || '/usr/share/freeradius/dictionary';
my $radius_host = $opt{radius_host} || die "You must specify a RADIUS
server!\n";
my $radius_port = $opt{radius_port} || '1812';
my $radius_secret = $opt{radius_secret} || die "You must specify a RADIUS
secret!\n";
my $radius_timeout = $opt{radius_timeout} || '3';
#
# Get username/password from file
#
my $upfilename = shift @ARGV;
die "No username/password file specified on command line\n" unless $upfilename;
sysopen(UPFILE, $upfilename, O_RDONLY) or
die "Could not open username/password file: $upfilename\n";
my $username = <UPFILE>;
my $password = <UPFILE>;
die "Username/password not found in file: $upfilename\n"
unless defined $username && defined $password;
chomp $username;
chomp $password;
close (UPFILE);
#
# Initialize RADIUS Authentication module
#
my ($ip, $netmask);
my $r = new Authen::Radius( Host => $radius_host.":".$radius_port,
Secret => $radius_secret,
TimeOut => $radius_timeout,
Debug => 0
);
$r->load_dictionary($radius_dictionary);
$r->add_attributes (
# User-Name
{ Name => 1, Value => $username, Type => 'string' },
# User-Password
{ Name => 2, Value => $password, Type => 'string' },
{ Name => 'NAS-Port-Type', Value => 'Virtual' }
);
$r->send_packet(ACCESS_REQUEST);
my $rcv = $r->recv_packet();
if (defined($rcv) and $rcv == ACCESS_ACCEPT) {
for my $attr ($r->get_attributes()) {
if ($attr->{'Name'} eq 'Framed-IP-Address') {
$ip = $attr->{'Value'};
}
}
if (defined $ip) {
# write Framed-IP-Address to the client configuration
# WARNING: this assumes no other configuration besides the IP
# exists in that file!
my $filename = $client_config_dir.$username;
unlink $filename;
sysopen(CLIENT, $filename, O_WRONLY|O_CREAT|O_TRUNC) or
die "Could not open client's config '$filename'\n";
print CLIENT "ifconfig-push $ip\n";
close (CLIENT);
}
} else {
die "Auth '$username' failed, RADIUS said: ".$r->strerror().' Code:
'.$r->get_error."\n";
}