diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 0f81937e..21a72e57 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -408,16 +408,16 @@ minimal/Ubuntu20.04: # We do not compile with PAM under address sanitizer since we are using co-routines # without instrumentation for sanitizer. -.asan/Fedora: +asan/clang/Fedora: stage: testing image: $CI_REGISTRY/$BUILD_IMAGES_PROJECT:$FEDORA_BUILD script: - - chmod o-w tests/data/raddb + - chmod -R o-w tests/data/raddb - git submodule update --init - autoreconf -fvi - - CFLAGS="-fsanitize=address -g -O2" LDFLAGS="-static-libasan" ./configure --without-pam --without-docker-tests + - CC=clang CFLAGS="-fsanitize=address -fno-optimize-sibling-calls -fno-omit-frame-pointer -g -O1" ./configure --without-pam --without-docker-tests --without-asan-broken-tests - make -j$JOBS - - make check -j$JOBS VERBOSE=1 + - make check -j$JOBS tags: - shared - linux diff --git a/configure.ac b/configure.ac index 5a9addc8..635d6807 100644 --- a/configure.ac +++ b/configure.ac @@ -14,7 +14,7 @@ gl_EARLY AM_PROG_AR AM_PROG_CC_C_O AC_PROG_SED -if test "$GCC" = "yes" && ! echo "$CC"|grep clang;then +if test "$GCC" = "yes" && ! expr "$CC" : clang >/dev/null 2>&1;then CFLAGS="$CFLAGS -Wall -Wno-strict-aliasing -Wextra -Wno-unused-parameter -Wno-sign-compare -Wno-missing-field-initializers -Wno-implicit-fallthrough -Wno-stringop-truncation" fi @@ -129,6 +129,16 @@ AC_ARG_WITH(docker-tests, AM_CONDITIONAL(ENABLE_DOCKER_TESTS, test "x$docker_tests" = xyes) +AC_ARG_WITH(asan-broken-tests, + AS_HELP_STRING([--without-asan-broken-tests], [disable any tests that cannot be run under asan]), + enable_asan_broken_tests=$withval, + enable_asan_broken_tests=yes) + +AC_MSG_CHECKING([whether to enable broken in asan tests]) +AC_MSG_RESULT([${enable_asan_broken_tests}]) + +AM_CONDITIONAL(DISABLE_ASAN_BROKEN_TESTS, test "x$enable_asan_broken_tests" = xno) + AC_ARG_WITH(kerberos-tests, AS_HELP_STRING([--with-kerberos-tests], [enable any tests requiring kerberos setup]), kerberos_tests=$withval, diff --git a/doc/sample.config b/doc/sample.config index 67d85dea..304d9bd2 100644 --- a/doc/sample.config +++ b/doc/sample.config @@ -405,7 +405,8 @@ rekey-method = ssl # Script to call when a client connects and obtains an IP. # The following parameters are passed on the environment. # REASON, VHOST, USERNAME, GROUPNAME, DEVICE, IP_REAL (the real IP of the client), -# IP_REAL_LOCAL (the local interface IP the client connected), IP_LOCAL +# REMOTE_HOSTNAME (the remotely advertised hostname), IP_REAL_LOCAL +# (the local interface IP the client connected), IP_LOCAL # (the local IP in the P-t-P connection), IP_REMOTE (the VPN IP of the client), # IPV6_LOCAL (the IPv6 local address if there are both IPv4 and IPv6 # assigned), IPV6_REMOTE (the IPv6 remote address), IPV6_PREFIX, and @@ -426,7 +427,7 @@ rekey-method = ssl # This script is to be called when the client's advertised hostname becomes # available. It will contain REASON with "host-update" value and the -# variable HOSTNAME in addition to the connect variables. +# variable REMOTE_HOSTNAME in addition to the connect variables. #host-update-script = /usr/bin/myhostnamescript diff --git a/src/common/snapshot.c b/src/common/snapshot.c index 1e02bf84..ed633af8 100644 --- a/src/common/snapshot.c +++ b/src/common/snapshot.c @@ -120,6 +120,12 @@ static int snapshot_add_entry(snapshot_t * snapshot, const char *filename, return retval; } +static int talloc_clear_htable(snapshot_t *s) +{ + htable_clear(&s->ht); + return 0; +} + int snapshot_init(void *pool, struct snapshot_t **snapshot, const char *prefix) { snapshot_t *new_snapshot = NULL; @@ -141,6 +147,7 @@ int snapshot_init(void *pool, struct snapshot_t **snapshot, const char *prefix) goto cleanup; htable_init(&new_snapshot->ht, snapshot_rehash, new_snapshot); + talloc_set_destructor(new_snapshot, talloc_clear_htable); *snapshot = new_snapshot; new_snapshot = NULL; diff --git a/src/main-user.c b/src/main-user.c index f54bfc2f..687f6b38 100644 --- a/src/main-user.c +++ b/src/main-user.c @@ -341,6 +341,7 @@ const char* script, *next_script = NULL; setenv("USERNAME", proc->username, 1); setenv("GROUPNAME", proc->groupname, 1); setenv("HOSTNAME", proc->hostname, 1); + setenv("REMOTE_HOSTNAME", proc->hostname, 1); setenv("DEVICE", proc->tun_lease.name, 1); setenv("USER_AGENT", proc->user_agent, 1); setenv("DEVICE_TYPE", proc->device_type, 1); diff --git a/src/occtl/occtl.c b/src/occtl/occtl.c index 2793c640..24bda75c 100644 --- a/src/occtl/occtl.c +++ b/src/occtl/occtl.c @@ -558,6 +558,7 @@ int main(int argc, char **argv) const char *file = NULL; void *gl_pool; cmd_params_st params; + int ret; memset(¶ms, 0, sizeof(params)); @@ -615,7 +616,9 @@ int main(int argc, char **argv) } /* handle all arguments as a command */ - exit(single_cmd(argc, argv, gl_pool, file, ¶ms)); + ret = single_cmd(argc, argv, gl_pool, file, ¶ms); + talloc_free(gl_pool); + exit(ret); } interactive: @@ -634,5 +637,6 @@ int main(int argc, char **argv) conn_close(conn); + talloc_free(gl_pool); return 0; } diff --git a/tests/Makefile.am b/tests/Makefile.am index 7e14e037..12efb39b 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -192,3 +192,8 @@ XFAIL_TESTS = $(xfail_scripts) TESTS_ENVIRONMENT = srcdir="$(srcdir)" \ top_builddir="$(top_builddir)" +if DISABLE_ASAN_BROKEN_TESTS +TESTS_ENVIRONMENT += DISABLE_ASAN_BROKEN_TESTS=1 +else +TESTS_ENVIRONMENT += DISABLE_ASAN_BROKEN_TESTS=0 +endif diff --git a/tests/common.sh b/tests/common.sh index 453b80b8..477d568c 100644 --- a/tests/common.sh +++ b/tests/common.sh @@ -30,12 +30,21 @@ if test -z "${OPENCONNECT}" || ! test -x ${OPENCONNECT};then exit 1 fi +if test "${DISABLE_ASAN_BROKEN_TESTS}" = 1;then + echo "Disabling worker isolation to enable asan" + ISOLATE_WORKERS=false +fi + if test -z "$NO_NEED_ROOT";then if test "$(id -u)" != "0";then echo "You need to run this script as root" exit 77 fi else + if test "${DISABLE_ASAN_BROKEN_TESTS}" = 1;then + echo "Skipping test requiring ldpreload" + exit 77 + fi SOCKDIR="${srcdir}/tmp/sockwrap.$$.tmp" mkdir -p $SOCKDIR export SOCKET_WRAPPER_DIR=$SOCKDIR diff --git a/tests/connect-script b/tests/connect-script index f266245d..4175da4f 100755 --- a/tests/connect-script +++ b/tests/connect-script @@ -14,6 +14,7 @@ verify_env_set() { verify_env_set "IP_REMOTE" verify_env_set "REASON" verify_env_set "HOSTNAME" +verify_env_set "REMOTE_HOSTNAME" verify_env_set "USERNAME" verify_env_set "USER_AGENT" verify_env_set "DEVICE_PLATFORM" diff --git a/tests/test-pass-script b/tests/test-pass-script index e702f34a..6be97528 100755 --- a/tests/test-pass-script +++ b/tests/test-pass-script @@ -80,7 +80,15 @@ echo " * Connecting to obtain cookie... " echo " * Re-connecting to force script run... " echo "!@#$%^&*()<>" | timeout 7 $OPENCONNECT -q --local-hostname='mylocalname' localhost:$PORT -u "sp@c/al" --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 -s /bin/true -sleep 5 +TIMEOUT=5 +while ! test -f ${builddir}/disconnect.ok; do + TIMEOUT=$(($TIMEOUT - 1)) + if [ $TIMEOUT -eq 0 ]; then + echo "Timed out waiting for ${builddir}/disconnect.ok (1)" + exit 1 + fi + sleep 1 +done if ! test -f ${builddir}/connect.ok;then echo "Connect script was not run" @@ -117,41 +125,59 @@ fi echo " * Re-connecting to force session stealing... " eval "$(grep COOKIE ${PARAMSFILE})" -echo ${COOKIE}| $OPENCONNECT localhost:$PORT -u "test2" --reconnect-timeout 0 --cookie-on-stdin --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 -s /bin/true --pid-file=${OPIDFILE} -b +echo ${COOKIE}| $OPENCONNECT --local-hostname='mylocalname' localhost:$PORT -u "test2" --reconnect-timeout 0 --cookie-on-stdin --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 -s /bin/true --pid-file=${OPIDFILE} -b -sleep 4 echo " - Pausing client" -if ! test -f ${OPIDFILE};then - echo "Could not find pid file" +TIMEOUT=4 +while ! test -f ${OPIDFILE}; do + TIMEOUT=$(($TIMEOUT - 1)) + if [ $TIMEOUT -eq 0 ]; then + echo "Timed out waiting for ${OPIDFILE}" exit 1 -fi -kill -s STOP $(cat ${OPIDFILE}) -sleep 12 + fi + sleep 1 +done -if ! test -f ${builddir}/connect.ok;then - echo "Connect script was not run (2)" +kill -s STOP $(cat ${OPIDFILE}) + +TIMEOUT=12 +while ! test -f ${builddir}/connect.ok; do + TIMEOUT=$(($TIMEOUT - 1)) + if [ $TIMEOUT -eq 0 ]; then + echo "Timed out waiting for ${builddir}/connect.ok" exit 1 -fi + fi + sleep 1 +done rm -f ${builddir}/connect.ok rm -f ${builddir}/disconnect.ok echo " * Re-connecting to steal previous IP address... " -echo ${COOKIE} | $OPENCONNECT -q localhost:$PORT -u "test2" --reconnect-timeout 0 --cookie-on-stdin --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 -s /bin/true --pid-file=${OPIDFILE2} -b +echo ${COOKIE} | $OPENCONNECT -q --local-hostname='mylocalname' localhost:$PORT -u "test2" --reconnect-timeout 0 --cookie-on-stdin --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 -s /bin/true --pid-file=${OPIDFILE2} -b echo " - Resuming (disconnected) client" kill -s CONT $(cat ${OPIDFILE}) -sleep 6 -if ! test -f ${builddir}/connect.ok;then - echo "Connect script was not run (3)" +TIMEOUT=6 +while ! test -f ${builddir}/connect.ok; do + TIMEOUT=$(($TIMEOUT - 1)) + if [ $TIMEOUT -eq 0 ]; then + echo "Timed out waiting for ${builddir}/connect.ok (3)" exit 1 -fi + fi + sleep 1 +done -if ! test -f ${builddir}/disconnect.ok;then - echo "Disconnect script was not run properly (3)" +TIMEOUT=6 +while ! test -f ${builddir}/disconnect.ok; do + TIMEOUT=$(($TIMEOUT - 1)) + if [ $TIMEOUT -eq 0 ]; then + echo "Timed out waiting for ${builddir}/disconnect.ok (3)" exit 1 -fi + fi + sleep 1 +done rm -f ${builddir}/connect.ok rm -f ${builddir}/disconnect.ok @@ -160,18 +186,24 @@ echo " - Killing all clients" sleep 2 test -f ${OPIDFILE2} && kill $(cat ${OPIDFILE2}) test -f ${OPIDFILE} && kill $(cat ${OPIDFILE}) -sleep 6 echo " - Last check of files" -if ! test -f ${builddir}/disconnect.ok;then - echo "Disconnect script was not run properly (4)" + +TIMEOUT=6 +while ! test -f ${builddir}/disconnect.ok; do + TIMEOUT=$(($TIMEOUT - 1)) + if [ $TIMEOUT -eq 0 ]; then + echo "Timed out waiting for ${builddir}/disconnect.ok (4)" exit 1 -fi + fi + sleep 1 +done + sleep 5 echo " - Check server status" -( echo "!@#$%^&*()<>" | $OPENCONNECT -q localhost:$PORT -u "sp@c/al" --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 --cookieonly >/dev/null 2>&1 ) || +( echo "!@#$%^&*()<>" | $OPENCONNECT --local-hostname='mylocalname' -q localhost:$PORT -u "sp@c/al" --servercert=d66b507ae074d03b02eafca40d35f87dd81049d3 --cookieonly >/dev/null 2>&1 ) || fail $PID "Could not receive cookie from server" echo " - Killing server" diff --git a/tests/test-script-multi-user b/tests/test-script-multi-user index 81a0c12f..a5e86ba2 100755 --- a/tests/test-script-multi-user +++ b/tests/test-script-multi-user @@ -30,6 +30,11 @@ USERNAME=test . `dirname $0`/common.sh +if test "${DISABLE_ASAN_BROKEN_TESTS}" = 1;then + echo "Skipping test requiring ldpreload" + exit 77 +fi + rm -f test-sleep.tmp OCCTL_SOCKET=./occtl-test-script-$$.socket