Commit 6e102346 authored by Faidon Liambotis's avatar Faidon Liambotis

Import Upstream version 1.3

parents
Stig Venaas <venaas@uninett.no>
Copyright (C) 2006-2009 Stig Venaas <venaas@uninett.no>
See the LICENSE file for licensing terms.
2007-09-21 1.0
2007-10-16 1.0p1
Fixed crash when servers were configured after first realm block
2007-12-24 1.1-alpha
Pretend option for validating configuration
Include option for including additional config files
Allows clients configured by IP prefix, dynamic clients
Server failover support
Rewriting of username attribute
Source address and port can be specified for requests
2008-05-14 1.1-beta
No longer looks for radsecproxy.conf in current directory
Rewrite block that allows removal of specified attributes
certificateNameCheck option for disabling CN/SubjectAltName check
matchCertificateAttribute now also supports CN matching
Forwarding of accounting messages, accountingServer option for realms
Supports multiple client blocks for same source address with different
certificate checks
Removed weekday from log timestamps
2008-07-24 1.1
Logging stationid attribute
Added LoopPrevention option
Failover also without status-server
Options for RetryCount and RetryInterval
Working accounting and AccountingResponse option
CRL checking and option for enabling it
2008-10-07 1.2
listenTCP and sourceTCP options renamed to listenTLS and sourceTLS
Old options deprecated but available for backwards compatiblity
Logging reply-message attribute from Reject messages
Contribution from Arne Schwabe
Rewrite blocks have new options addAttribute and modifyAttribute
rewriteIn (replacing rewrite) and rewriteOut in client and server
blocks for specifying rewrite on input/output. rewrite deprecated
but available as an alias for rewriteIn for backwards compatibility.
rewritein rewriteout rewrite
regular expressions in realms etc can now be more advanced, including
use of "or".
cacheExpiry option in tls blocks for specifying expiry time for the
cache of CA certificates and CRLs. This is particularly useful for
regularly updating CRLs.
Some logging has been made more informative
2008-12-04 1.3-alpha
Support for TCP and DTLS transports (type tcp, type dtls)
Listen... options can be specified multiple times
Dynamic server discovery
DuplicateInterval option in client block for specifying for how
long a request/reply shall be stored for duplicate detection
Support for RADIUS TTL (hopcount) attribute. Decrements value of
the TTL attribute if present, discards message if becomes 0.
If addTTL option is used, the TTL attribute is added with the
specified value if the forwarded message does not have one.
PolicyOID option can be used to require certain CA policies.
2009-02-18 1.3-beta
Client and Server blocks may contain multiple host options.
Configure (Makefile) options for specifying which transports
should be supported in a build.
2009-03-12 1.3
Fixed some very minor bugs
Changed log levels for some messages, made loglevel 2 default
This diff is collapsed.
The radsecproxy source code is subject to two licenses, you may pick
the one that best suits your needs.
The radsecproxy source code is subject to the terms of the GNU General
Public License Version 2 or later (GPL).
Alternatively the radsecproxy source code is subject to the terms of the
below BSD style license.
* Copyright (c) 2006-2009, UNINETT AS
* 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 distribution.
* * Neither the name of the UNINETT AS nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY UNINETT AS ``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 UNINETT AS 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.
CFLAGS = -g -Wall -pedantic -pthread -DRADPROT_UDP -DRADPROT_TLS
# -DRADPROT_TCP -DRADPROT_DTLS
LDFLAGS = -lssl
OBJ = util.o debug.o list.o hash.o gconfig.o tlv11.o hostport.o radmsg.o udp.o tcp.o tls.o dtls.o tlscommon.o radsecproxy.o
all: radsecproxy
radsecproxy: $(OBJ)
$(CC) $(CFLAGS) $(OBJ) $(LDFLAGS) -o radsecproxy
catgconf: util.o debug.o gconfig.o catgconf.o
$(CC) $(CFLAGS) util.o debug.o gconfig.o catgconf.o -o catgconf
clean:
rm -f $(OBJ) catgconf.o radsecproxy catgconf
man:
docbook2man.pl --to-stdout radsecproxy.conf.5.xml > radsecproxy.conf.5
html:
openjade -E10000 -t sgml-raw -d /usr/share/sgml/docbook/dsssl-stylesheets-1.79/html/docbook.dsl -o radsecproxy.conf.5.html radsecproxy.conf.5.xml
sbin_PROGRAMS = radsecproxy
radsecproxy_SOURCES = radsecproxy.c \
tlscommon.c \
gconfig.c \
util.c \
debug.c \
list.c \
hash.c \
tlv11.c \
hostport.c \
radmsg.c \
udp.c \
tcp.c \
tls.c \
dtls.c \
radsecproxy.h \
tlscommon.h \
gconfig.h \
debug.h \
util.h \
list.h \
hash.h \
tlv11.h \
hostport.h \
radmsg.h \
udp.h \
tcp.h \
tls.h \
dtls.h
radsecproxy_CFLAGS = -g @SSL_CFLAGS@ @TARGET_CFLAGS@
radsecproxy_LDFLAGS = @SSL_LDFLAGS@ @TARGET_LDFLAGS@
radsecproxy_LDADD = @SSL_LIBS@
dist_sysconf_DATA = $(srcdir)/radsecproxy.conf-example
dist_man_MANS = radsecproxy.1 radsecproxy.conf.5
This diff is collapsed.
This is radsecproxy 1.3 from March 12, 2009
radsecproxy is a generic RADIUS proxy that can support various
RADIUS clients over UDP or TLS (RadSec).
It should build on most Linux and BSD platforms by simply typing
"make". You may also try to use autoconf. It is possible to
specify which RADIUS transport the build should support. With
just doing "make" one will support only UDP and TLS. See the
Makefile for how to change this. With autoconf (configure) there
will normally be support for all transport. You can use the
configure options --enable-udp, --enable-tcp, --enable-tls and
--enable-dtls where each of them may be set to yes or no to
enable or disable them.
To use it you need to create a config file which normally is
called "/etc/radsecproxy.conf". You can also specify the location
with the "-c" command line option (see below). For further
instructions, please see the enclosed example file and the
documentation at
http://software.uninett.no/radsecproxy/?page=documentation
There are five options that may be specified on the command line.
"-c configfile" to specify a non-default config file path;
"-d loglevel" to set a loglevel of 1, 2, 3 or 4 where 4 is the most
detailed; and "-f" to run the proxy in the foreground with logging
to stderr. Without "-f" the default is to detach as a daemon and
log to syslog. "-v" just prints version information and exits, while
"-p" (pretend) makes the proxy go through the configuration files as
normal, but stops before creating any sockets or doing any serious
work. This is useful for validating config files.
Thanks to Stefan Winter and Andreas Solberg for talking me into
doing this, and the funding from GEANT2. Stefan as well as Kolbjørn
Barmen, Ralf Paffrath and Maja Wolniewicz have helped with early
testing of the code.
All of the above plus Milan Sova have provided good feedback on
several implementation choices. Finally thanks to Hans Zandbelt
for providing the autoconf stuff. I may have forgotten someone,
let me know if you feel left out.
For more information, feedback etc. please see the information
at http://software.uninett.no/radsecproxy/
Stig Venaas <venaas@uninett.no> -- 2009.03.12
dnl Based on the one from the Boinc project by Reinhard
AC_DEFUN([AX_CHECK_SSL],
[AC_MSG_CHECKING(for OpenSSL)
SSL_DIR=
found_ssl="no"
AC_ARG_WITH(ssl,
AC_HELP_STRING([--with-ssl],
[Use SSL (in specified installation directory)]),
[check_ssl_dir="$withval"],
[check_ssl_dir=])
for dir in $check_ssl_dir /usr /usr/local/ssl /usr/lib/ssl /usr/ssl /usr/pkg /usr/local ; do
ssldir="$dir"
if test -f "$dir/include/openssl/ssl.h"; then
found_ssl="yes";
SSL_DIR="${ssldir}"
SSL_CFLAGS="-I$ssldir/include -I$ssldir/include/openssl";
break;
fi
if test -f "$dir/include/ssl.h"; then
found_ssl="yes";
SSL_DIR="${ssldir}"
SSL_CFLAGS="-I$ssldir/include/";
break
fi
done
AC_MSG_RESULT($found_ssl)
if test x_$found_ssl != x_yes; then
AC_MSG_ERROR([
----------------------------------------------------------------------
Cannot find SSL libraries.
Please install OpenSSL or specify installation directory with
--with-ssl=(dir).
----------------------------------------------------------------------
])
else
printf "OpenSSL found in $ssldir\n";
SSL_LIBS="-lssl -lcrypto";
SSL_LDFLAGS="-L$ssldir/lib";
AC_DEFINE_UNQUOTED([USE_OPENSSL],[1],
["Define to 1 if you want to use the OpenSSL crypto library"])
AC_SUBST(SSL_CFLAGS)
AC_SUBST(SSL_LDFLAGS)
AC_SUBST(SSL_LIBS)
fi
])dnl
This diff is collapsed.
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include "debug.h"
#include "gconfig.h"
void listconfig(struct gconffile **cf, char *block, int compact) {
char *opt = NULL, *val = NULL;
int conftype;
for (;;) {
free(opt);
free(val);
getconfigline(cf, block, &opt, &val, &conftype);
if (!opt)
return;
if (conftype == CONF_STR && !strcasecmp(opt, "include")) {
if (!pushgconfpaths(cf, val))
debugx(1, DBG_ERR, "failed to include config file %s", val);
continue;
}
switch (conftype) {
case CONF_STR:
if (block)
printf(compact ? "%s=%s;" : "\t%s=%s\n", opt, val);
else
printf("%s=%s\n", opt, val);
break;
case CONF_CBK:
printf("%s %s {%s", opt, val, compact ? "" : "\n");
listconfig(cf, val, compact);
printf("}\n");
break;
default:
printf("Unsupported config type\n");
}
}
}
int main(int argc, char **argv) {
int c, compact = 0;
struct gconffile *cfs;
debug_init("catgconf");
debug_set_level(DBG_WARN);
while ((c = getopt(argc, argv, "c")) != -1) {
switch (c) {
case 'c':
compact = 1;
break;
default:
goto usage;
}
}
if (argc - optind != 1)
goto usage;
cfs = openconfigfile(argv[optind]);
listconfig(&cfs, NULL, compact);
return 0;
usage:
debug(DBG_ERR, "Usage:\n%s [ -c ] configfile", argv[0]);
exit(1);
}
#! /bin/sh
# Wrapper for compilers which do not understand `-c -o'.
scriptversion=2005-05-14.22
# Copyright (C) 1999, 2000, 2003, 2004, 2005 Free Software Foundation, Inc.
# Written by Tom Tromey <tromey@cygnus.com>.
#
# 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; either version 2, or (at your option)
# any later version.
#
# 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 Street, Fifth Floor, Boston, MA 02110-1301, USA.
# As a special exception to the GNU General Public License, if you
# distribute this file as part of a program that contains a
# configuration script generated by Autoconf, you may include it under
# the same distribution terms that you use for the rest of that program.
# This file is maintained in Automake, please report
# bugs to <bug-automake@gnu.org> or send patches to
# <automake-patches@gnu.org>.
case $1 in
'')
echo "$0: No command. Try \`$0 --help' for more information." 1>&2
exit 1;
;;
-h | --h*)
cat <<\EOF
Usage: compile [--help] [--version] PROGRAM [ARGS]
Wrapper for compilers which do not understand `-c -o'.
Remove `-o dest.o' from ARGS, run PROGRAM with the remaining
arguments, and rename the output as expected.
If you are trying to build a whole package this is not the
right script to run: please start by reading the file `INSTALL'.
Report bugs to <bug-automake@gnu.org>.
EOF
exit $?
;;
-v | --v*)
echo "compile $scriptversion"
exit $?
;;
esac
ofile=
cfile=
eat=
for arg
do
if test -n "$eat"; then
eat=
else
case $1 in
-o)
# configure might choose to run compile as `compile cc -o foo foo.c'.
# So we strip `-o arg' only if arg is an object.
eat=1
case $2 in
*.o | *.obj)
ofile=$2
;;
*)
set x "$@" -o "$2"
shift
;;
esac
;;
*.c)
cfile=$1
set x "$@" "$1"
shift
;;
*)
set x "$@" "$1"
shift
;;
esac
fi
shift
done
if test -z "$ofile" || test -z "$cfile"; then
# If no `-o' option was seen then we might have been invoked from a
# pattern rule where we don't need one. That is ok -- this is a
# normal compilation that the losing compiler can handle. If no
# `.c' file was seen then we are probably linking. That is also
# ok.
exec "$@"
fi
# Name of file we expect compiler to create.
cofile=`echo "$cfile" | sed -e 's|^.*/||' -e 's/\.c$/.o/'`
# Create the lock directory.
# Note: use `[/.-]' here to ensure that we don't use the same name
# that we are using for the .o file. Also, base the name on the expected
# object file name, since that is what matters with a parallel build.
lockdir=`echo "$cofile" | sed -e 's|[/.-]|_|g'`.d
while true; do
if mkdir "$lockdir" >/dev/null 2>&1; then
break
fi
sleep 1
done
# FIXME: race condition here if user kills between mkdir and trap.
trap "rmdir '$lockdir'; exit 1" 1 2 15
# Run the compile.
"$@"
ret=$?
if test -f "$cofile"; then
mv "$cofile" "$ofile"
elif test -f "${cofile}bj"; then
mv "${cofile}bj" "$ofile"
fi
rmdir "$lockdir"
exit $ret
# Local Variables:
# mode: shell-script
# sh-indentation: 2
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-end: "$"
# End:
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
AC_INIT(radsecproxy, 1.3, venaas@uninett.no)
AM_INIT_AUTOMAKE
AC_PROG_CC
AM_PROG_CC_C_O
udp=yes
AC_ARG_ENABLE(udp,
[ --enable-udp whether to enable UDP transport: yes/no; default yes ],
[ if test "x$enableval" = "xyes" -o "x$enableval" = "xno" ; then
udp=$enableval
else
echo "--enable-udp argument must be yes or no"
exit -1
fi
])
tcp=yes
AC_ARG_ENABLE(tcp,
[ --enable-tcp whether to enable TCP transport: yes/no; default yes ],
[ if test "x$enableval" = "xyes" -o "x$enableval" = "xno" ; then
tcp=$enableval
else
echo "--enable-tcp argument must be yes or no"
exit -1
fi
])
tls=yes
AC_ARG_ENABLE(tls,
[ --enable-tls whether to enable TLS (RadSec) transport: yes/no; default yes ],
[ if test "x$enableval" = "xyes" -o "x$enableval" = "xno" ; then
tls=$enableval
else
echo "--enable-tls argument must be yes or no"
exit -1
fi
])
dtls=yes
AC_ARG_ENABLE(dtls,
[ --enable-dtls whether to enable DTLS transport: yes/no; default yes ],
[ if test "x$enableval" = "xyes" -o "x$enableval" = "xno" ; then
dtls=$enableval
else
echo "--enable-dtls argument must be yes or no"
exit -1
fi
])
dnl Check if we're on Solaris and set CFLAGS accordingly
AC_CANONICAL_SYSTEM
case "${target_os}" in
solaris*)
TARGET_CFLAGS="-mt -DSYS_SOLARIS9 -D_POSIX_PTHREAD_SEMANTICS"
TARGET_LDFLAGS="-lpthread -lsocket -lnsl"
;;
*)
TARGET_CFLAGS="-Wall -pedantic -pthread"
TARGET_LDFLAGS=""
esac
dnl Adding enabled options
if test "x$udp" = "xyes" ; then
echo "UDP transport enabled"
TARGET_CFLAGS="$TARGET_CFLAGS -DRADPROT_UDP"
fi
if test "x$tcp" = "xyes" ; then
echo "TCP transport enabled"
TARGET_CFLAGS="$TARGET_CFLAGS -DRADPROT_TCP"
fi
if test "x$tls" = "xyes" ; then
echo "TLS (RadSec) transport enabled"
TARGET_CFLAGS="$TARGET_CFLAGS -DRADPROT_TLS"
fi
if test "x$dtls" = "xyes" ; then
echo "DTLS transport enabled"
TARGET_CFLAGS="$TARGET_CFLAGS -DRADPROT_DTLS"
fi
AC_SUBST(TARGET_CFLAGS)
AC_SUBST(TARGET_LDFLAGS)
AX_CHECK_SSL
AC_OUTPUT(Makefile)
/*
* Copyright (C) 2007 Stig Venaas <venaas@uninett.no>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*/
#ifndef SYS_SOLARIS9
#include <stdint.h>
#endif
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <strings.h>
#include <time.h>
#include <sys/time.h>
#include <syslog.h>
#include <errno.h>
#include "debug.h"
#include "util.h"
static char *debug_ident = NULL;
static uint8_t debug_level = DBG_INFO;
static char *debug_filepath = NULL;
static FILE *debug_file = NULL;
static int debug_syslogfacility = 0;
static uint8_t debug_timestamp = 0;
void debug_init(char *ident) {
debug_file = stderr;
setvbuf(debug_file, NULL, _IONBF, 0);
debug_ident = ident;
}
void debug_set_level(uint8_t level) {
switch (level) {
case 1:
debug_level = DBG_ERR;
return;
case 2:
debug_level = DBG_WARN;
return;
case 3:
debug_level = DBG_INFO;
return;
case 4:
debug_level = DBG_DBG;
return;
}
}
void debug_timestamp_on() {
debug_timestamp = 1;
}
uint8_t debug_get_level() {
return debug_level;
}
int debug_set_destination(char *dest) {
static const char *facstrings[] = { "LOG_DAEMON", "LOG_MAIL", "LOG_USER", "LOG_LOCAL0",
"LOG_LOCAL1", "LOG_LOCAL2", "LOG_LOCAL3", "LOG_LOCAL4",
"LOG_LOCAL5", "LOG_LOCAL6", "LOG_LOCAL7", NULL };
static const int facvals[] = { LOG_DAEMON, LOG_MAIL, LOG_USER, LOG_LOCAL0,
LOG_LOCAL1, LOG_LOCAL2, LOG_LOCAL3, LOG_LOCAL4,
LOG_LOCAL5, LOG_LOCAL6, LOG_LOCAL7 };
extern int errno;
int i;
if (!strncasecmp(dest, "file:///", 8)) {
debug_filepath = stringcopy(dest + 7, 0);
debug_file = fopen(debug_filepath, "a");
if (!debug_file) {
debug_file = stderr;
debugx(1, DBG_ERR, "Failed to open logfile %s\n%s",
debug_filepath, strerror(errno));
}
setvbuf(debug_file, NULL, _IONBF, 0);
return 1;
}
if (!strncasecmp(dest, "x-syslog://", 11)) {
dest += 11;
if (*dest == '/')
dest++;
if (*dest) {
for (i = 0; facstrings[i]; i++)
if (!strcasecmp(dest, facstrings[i]))
break;
if (!facstrings[i])
debugx(1, DBG_ERR, "Unknown syslog facility %s", dest);
debug_syslogfacility = facvals[i];
} else
debug_syslogfacility = LOG_DAEMON;
openlog(debug_ident, LOG_PID, debug_syslogfacility);
return 1;
}
debug(DBG_ERR, "Unknown log destination, exiting %s", dest);
exit(1);
}
void debug_reopen_log() {
extern int errno;
/* not a file, noop, return success */
if (!debug_filepath) {
debug(DBG_ERR, "skipping reopen");
return;
}
if (debug_file != stderr)
fclose(debug_file);
debug_file = fopen(debug_filepath, "a");
if (debug_file)
debug(DBG_ERR, "Reopened logfile %s", debug_filepath);
else {
debug_file = stderr;
debug(DBG_ERR, "Failed to open logfile %s, using stderr\n%s",
debug_filepath, strerror(errno));
}
setvbuf(debug_file, NULL, _IONBF, 0);
}
void debug_logit(uint8_t level, const char *format, va_list ap) {
struct timeval now;
char *timebuf;
int priority;
if (debug_syslogfacility) {
switch (level) {
case DBG_DBG:
priority = LOG_DEBUG;
break;
case DBG_INFO:
priority = LOG_INFO;
break;
case DBG_WARN:
priority = LOG_WARNING;
break;
case DBG_ERR:
priority = LOG_ERR;
break;
default:
priority = LOG_DEBUG;
}
vsyslog(priority, format, ap);
} else {
if (debug_timestamp && (timebuf = malloc(256))) {
gettimeofday(&now, NULL);
ctime_r(&now.tv_sec, timebuf);
timebuf[strlen(timebuf) - 1] = '\0';
fprintf(debug_file, "%s: ", timebuf + 4);
free(timebuf);
}
vfprintf(debug_file, format, ap);
fprintf(debug_file, "\n");
}
}
void debug(uint8_t level, char *format, ...) {
va_list ap;
if (level < debug_level)
return;
va_start(ap, format);
debug_logit(level, format, ap);
va_end(ap);
}
void debugx(int status, uint8_t level, char *format, ...) {
if (level >= debug_level) {
va_list ap;
va_start(ap, format);
debug_logit(level, format, ap);
va_end(ap);
}
exit(status);
}
/*
* Copyright (C) 2007 Stig Venaas <venaas@uninett.no>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*/
#ifndef SYS_SOLARIS9
#include <stdint.h>