From b179d94eb3b87e46721e7060386ff1a2f64669a6 Mon Sep 17 00:00:00 2001 From: Arne Schwabe Date: Sat, 21 Jul 2012 01:11:36 +0200 Subject: Update openvpn to Version 2.3_alpha3 --- openvpn/ChangeLog | 171 ++++++++++++- openvpn/INSTALL | 150 +++++++----- openvpn/INSTALL-win32.txt | 25 ++ openvpn/TODO.IPv6 | 35 ++- openvpn/configure.ac | 84 ++++++- openvpn/distro/rpm/openvpn.spec.in | 47 +--- openvpn/doc/Makefile.am | 5 +- openvpn/doc/README.plugins | 47 ++++ openvpn/doc/management-notes.txt | 31 +++ openvpn/doc/openvpn.8 | 18 +- openvpn/msvc-build.bat | 1 + openvpn/msvc-dev.bat | 2 +- openvpn/msvc-env.bat | 2 - openvpn/sample/Makefile.am | 1 + openvpn/sample/sample-plugins/defer/README | 16 ++ openvpn/sample/sample-plugins/defer/build | 15 ++ openvpn/sample/sample-plugins/defer/simple.c | 305 ++++++++++++++++++++++++ openvpn/sample/sample-plugins/defer/simple.def | 6 + openvpn/sample/sample-plugins/defer/winbuild | 18 ++ openvpn/sample/sample-plugins/log/build | 15 ++ openvpn/sample/sample-plugins/log/log.c | 184 ++++++++++++++ openvpn/sample/sample-plugins/log/log_v3.c | 247 +++++++++++++++++++ openvpn/sample/sample-plugins/log/winbuild | 18 ++ openvpn/sample/sample-plugins/simple/README | 16 ++ openvpn/sample/sample-plugins/simple/build | 15 ++ openvpn/sample/sample-plugins/simple/simple.c | 120 ++++++++++ openvpn/sample/sample-plugins/simple/simple.def | 6 + openvpn/sample/sample-plugins/simple/winbuild | 18 ++ openvpn/src/Makefile.am | 5 +- openvpn/src/openvpn/Makefile.am | 6 +- openvpn/src/openvpn/common.h | 2 - openvpn/src/openvpn/crypto.c | 6 - openvpn/src/openvpn/error.c | 9 +- openvpn/src/openvpn/error.h | 4 - openvpn/src/openvpn/fdmisc.c | 2 +- openvpn/src/openvpn/init.c | 246 +++++++------------ openvpn/src/openvpn/manage.c | 64 +---- openvpn/src/openvpn/manage.h | 23 +- openvpn/src/openvpn/misc.c | 6 - openvpn/src/openvpn/mroute.c | 2 +- openvpn/src/openvpn/openvpn.c | 37 ++- openvpn/src/openvpn/openvpn.vcxproj | 10 +- openvpn/src/openvpn/options.c | 262 +++----------------- openvpn/src/openvpn/options.h | 64 +---- openvpn/src/openvpn/pkcs11.c | 2 +- openvpn/src/openvpn/proxy.c | 267 ++------------------- openvpn/src/openvpn/proxy.h | 30 +-- openvpn/src/openvpn/ps.c | 6 +- openvpn/src/openvpn/route.c | 84 +++++-- openvpn/src/openvpn/route.h | 1 - openvpn/src/openvpn/socket.c | 69 +++--- openvpn/src/openvpn/socket.h | 2 +- openvpn/src/openvpn/socks.c | 41 ++-- openvpn/src/openvpn/socks.h | 3 +- openvpn/src/openvpn/ssl_backend.h | 36 +-- openvpn/src/openvpn/ssl_openssl.c | 39 +-- openvpn/src/openvpn/ssl_polarssl.c | 34 +-- openvpn/src/openvpn/ssl_polarssl.h | 1 - openvpn/src/openvpn/syshead.h | 31 +-- openvpn/src/openvpn/tun.c | 46 +++- openvpn/src/openvpn/win32.c | 6 +- openvpn/src/plugins/Makefile.am | 15 ++ openvpn/src/plugins/README | 47 ---- openvpn/src/plugins/auth-pam/Makefile | 32 --- openvpn/src/plugins/auth-pam/Makefile.am | 27 +++ openvpn/src/plugins/auth-pam/README | 74 ------ openvpn/src/plugins/auth-pam/README.auth-pam | 74 ++++++ openvpn/src/plugins/auth-pam/auth-pam.c | 18 +- openvpn/src/plugins/auth-pam/auth-pam.exports | 4 + openvpn/src/plugins/auth-pam/pamdl.c | 8 +- openvpn/src/plugins/auth-pam/pamdl.h | 4 +- openvpn/src/plugins/defer/README | 16 -- openvpn/src/plugins/defer/build | 15 -- openvpn/src/plugins/defer/simple.c | 305 ------------------------ openvpn/src/plugins/defer/simple.def | 6 - openvpn/src/plugins/defer/winbuild | 18 -- openvpn/src/plugins/down-root/Makefile | 18 -- openvpn/src/plugins/down-root/Makefile.am | 23 ++ openvpn/src/plugins/down-root/README | 29 --- openvpn/src/plugins/down-root/README.down-root | 29 +++ openvpn/src/plugins/down-root/down-root.c | 6 +- openvpn/src/plugins/down-root/down-root.exports | 4 + openvpn/src/plugins/examples/README | 16 -- openvpn/src/plugins/examples/build | 15 -- openvpn/src/plugins/examples/log.c | 184 -------------- openvpn/src/plugins/examples/log_v3.c | 247 ------------------- openvpn/src/plugins/examples/simple.c | 120 ---------- openvpn/src/plugins/examples/simple.def | 6 - openvpn/src/plugins/examples/winbuild | 18 -- openvpn/tests/t_client.sh.in | 12 +- openvpn/version.m4 | 2 +- 91 files changed, 2126 insertions(+), 2330 deletions(-) create mode 100644 openvpn/doc/README.plugins create mode 100644 openvpn/sample/sample-plugins/defer/README create mode 100755 openvpn/sample/sample-plugins/defer/build create mode 100644 openvpn/sample/sample-plugins/defer/simple.c create mode 100755 openvpn/sample/sample-plugins/defer/simple.def create mode 100755 openvpn/sample/sample-plugins/defer/winbuild create mode 100755 openvpn/sample/sample-plugins/log/build create mode 100644 openvpn/sample/sample-plugins/log/log.c create mode 100644 openvpn/sample/sample-plugins/log/log_v3.c create mode 100755 openvpn/sample/sample-plugins/log/winbuild create mode 100644 openvpn/sample/sample-plugins/simple/README create mode 100755 openvpn/sample/sample-plugins/simple/build create mode 100644 openvpn/sample/sample-plugins/simple/simple.c create mode 100755 openvpn/sample/sample-plugins/simple/simple.def create mode 100755 openvpn/sample/sample-plugins/simple/winbuild mode change 100644 => 100755 openvpn/src/openvpn/openvpn.vcxproj create mode 100644 openvpn/src/plugins/Makefile.am delete mode 100644 openvpn/src/plugins/README delete mode 100755 openvpn/src/plugins/auth-pam/Makefile create mode 100644 openvpn/src/plugins/auth-pam/Makefile.am delete mode 100644 openvpn/src/plugins/auth-pam/README create mode 100644 openvpn/src/plugins/auth-pam/README.auth-pam create mode 100644 openvpn/src/plugins/auth-pam/auth-pam.exports delete mode 100644 openvpn/src/plugins/defer/README delete mode 100755 openvpn/src/plugins/defer/build delete mode 100644 openvpn/src/plugins/defer/simple.c delete mode 100755 openvpn/src/plugins/defer/simple.def delete mode 100755 openvpn/src/plugins/defer/winbuild delete mode 100755 openvpn/src/plugins/down-root/Makefile create mode 100644 openvpn/src/plugins/down-root/Makefile.am delete mode 100644 openvpn/src/plugins/down-root/README create mode 100644 openvpn/src/plugins/down-root/README.down-root create mode 100644 openvpn/src/plugins/down-root/down-root.exports delete mode 100644 openvpn/src/plugins/examples/README delete mode 100755 openvpn/src/plugins/examples/build delete mode 100644 openvpn/src/plugins/examples/log.c delete mode 100644 openvpn/src/plugins/examples/log_v3.c delete mode 100644 openvpn/src/plugins/examples/simple.c delete mode 100755 openvpn/src/plugins/examples/simple.def delete mode 100755 openvpn/src/plugins/examples/winbuild (limited to 'openvpn') diff --git a/openvpn/ChangeLog b/openvpn/ChangeLog index d4983440..9205528e 100644 --- a/openvpn/ChangeLog +++ b/openvpn/ChangeLog @@ -1,5 +1,174 @@ OpenVPN Change Log -Copyright (C) 2002-2011 OpenVPN Technologies, Inc. +Copyright (C) 2002-2012 OpenVPN Technologies, Inc. + +2012.07.20 -- Version 2.3_alpha3 +Arne Schwabe (1): + Fix compiling with --disable-management + +Gert Doering (1): + Repair "tap server" mode brokenness caused by fallout + +Heiko Hund (4): + make non-blocking connect work on Windows + don't treat socket related errors special anymore + remove unused show_connection_list debug function + add option --management-query-proxy + +2012.06.29 -- Version 2.3_alpha2 +Adriaan de Jong (11): + Fixed off-by-one in serial length calculation + Migrated x509_get_subject to use of the garbage collector + Migrated x509_get_serial to use the garbage collector + Migrated x509_get_sha1_hash to use the garbage collector + Ensure sys/un.h autoconf detection includes sys/socket.h + Added support for new PolarSSL 1.1 RNG + Added a configuration option to enable prediction resistance in the PolarSSL random number generator. + Use POLARSSL_CFLAGS instead of POLARSSL_CRYPTO_CFLAGS in configure.ac + Removed support for PolarSSL < 1.1 + Updated README.polarssl with build system changes. + Removed stray "Fox-IT hardening" string. + +Alon Bar-Lev (94): + build: version should not contain '-' + package: rpm: strip should be handled by package management + cleanup: options.c: remove redundant include + cleanup: remove C++ warnings + cleanup: win32.c: wrong printf format + cleanup: remove redundant ';' + cleanup: crypto_openssl.c: remove support for pre-openssl-0.9.6 + cleanup: tun.c: fix incorrect option in message (ip-win32) + cleanup: memcmp.c: remove unused source + fixup: init.c: add missing conditional for ENABLE_CLIENT_CR + build: correct place to alter WINVER is at build system + Update .gitignore + build: handle printf style format in mingw + build: rename plugin directory to plugins + build: plugins: properly use CC, CFLAGS and LDFLAGS + build: we need the sample.ovpn in future + Remove install-win32 + Remove easy-rsa + Remove tap-win32 + cleanup: rename tap-windows function from win32 to win + build: remove windows specific build system + build: split acinclude.m4 into m4/* + build: m4/ax_varargs.m4: cleanup + build: m4/ax_emptyarray.m4: cleanup + build: m4/ax_socklen_t.m4: cleanup + build: autotools: first pass of trivial autotools changes + build: autoconf: remove OPENVPN_ADD_LIBS useless macro + build: remove awk and non-standard autoconf output processing + build: standard directory layout + build: add libtool + windows resources for executables + build: autoconf: commands as environment + build: libdl usage + build: properly detect and use socket libs + build: autoconf: minor cleanups + build: proper selinux detection and usage + build: distribute pkg.m4 + build: proper pkcs11-helper detection and usage + build: properly process lzo-stub + build: proper lzo detection and usage + build: proper crypto detection and usage + build: autoconf: update defaults for options + build: win-msvc: msbuild format + build: move out config.h include from syshead + build: split out compat + build: move gettimeofday() emulation to compat + build: move daemon() emulation into compat + build: move inet_ntop(), inet_pton() emulation into compat + cleanup: move console related function into its own module + build: move wrappers into platform module + build: windows: install version.sh to allow installer read version + build: distribute samples in windows + build: use tap-windows.h as external dependency + build: ax_varargs.m4: fixups + build: autoconf: misc sockets fixups + build: enable lzo by default + build: windows: set vendor to openvpn project + cleanups + build: assume dlfcn is available on all supported platforms + build: openbsd: detect netinet/ip.h correctly + build: tap: search for tap header + build: msvc: upgrade to Visual Studio 2010 + fixups + Enable pedantic in windows compilation + cleanup: flags should not be bool + cleanup: avoid using ~0 - generic + cleanup: avoid using ~0 - ipv6 + cleanup: avoid using ~0 - netmask + cleanup: avoid using ~0 - windows + cleanup: gc usage + build: fix some statement left from conversion + build: properly detect netinet/ip.h structs + build: properly detect TUNSETPERSIST + cleanup: plugin: support C++ plugin + cleanup: remove C++ comments + cleanup: add .gitattributes to control eol style explicitly + crash: packet_id_debug_print: sl may be null + build: use stdbool.h if available + build: fix typo in --enable-save-password + build: windows: convert resources to UTF-8 + build: check minimum polarssl version + cleanup: update .gitignore + cleanup: spec: make space/tab consistent + build: spec: we support openssl >= 0.9.7 + build: insall README* document using build system + build: detect sys/wait.h required for *bsd + build: add git revision to --version output if build from git repository + build: cleanup: yet another forgotten brackets + build: update INSTALL to recent changes + build: support platforms that does not need explicit tun headers + build: do not support mtu 1500 * semi-fixed for NetBSD, 28.2.10, always do tun0 destroy / tun0 create before actual ifconfig -- tunnel still lingers after OpenVPN quits + * 2011-09-16 fixed in platform cleanup, commit 8ca19c014c149cf69 + 4b.) verify this - on FreeBSD, tun0 is auto-destroyed if created by opening /dev/tun (and lingers if created by "ifconfig tun0 create") -> use for persistant tunnels on not-linux? + * 2012-06-10 tun interface behaviour is documented in "man tun(4)" + 5.) add new option "ifconfig-ipv6-push" (per-client static IPv6 assignment, -> radiusplugin, etc) @@ -48,12 +58,17 @@ tun0: flags=8051 mtu 1500 6.) add new option "route-ipv6-gateway" + * 2012-06-09 - decided there is no current need (but fairly trivial) + 7.) add "full" gateway handling for IPv6 in route.c (right now, the routes are just sent down the tun interface, if the operating system in questions supports that, without care for the gateway address - which does not work for gateways that are supposed to point elsewhere. Also, it doesn't work for TAP interfaces. + * 2012-06-09 use "dev tun" for tun devices, "via $gateway" for tap + (and purposely do not support off-link routes) + 8.) full IPv6 support for TAP interfaces (main issue should be routes+gateway - and testing :-) ) @@ -62,8 +77,16 @@ tun0: flags=8051 mtu 1500 17:51:14.075412 fe:ab:6e:c5:53:71 > 33:33:ff:00:00:01, ethertype IPv6 (0x86dd), length 86: 2001:608:4:a053::1:0 > ff02::1:ff00:1: ICMP6, neighbor solicitation, who has 2001:608:4:a001::1, length 32 + * 2012-06-09 missing gateway support implemented + +8a.) how is iroute-via-tap supposed to work?? + * 2012-06-10 - answer: not at all, OpenVPN doesn't do "iroute" in + tap mode - set up "route-ipv6" with gateway address = individual + client's tap0 address to get the per-client routes + + 9.) verify that iroute-ipv6 and route-ipv6 interact in the same way as documented for iroute/route: @@ -113,6 +136,8 @@ tun0: flags=8051 mtu 1500 (openvpn-devel, Subject: OpenBSD) - test + * 2012-02-05 platform cleanup, commit 82d4e12068774b0a6ca + 17.) client-option (Elwood) - ignore-v6-push-options yes/no - ignore-v6-route-push ("as for IPv4 routes") @@ -150,13 +175,15 @@ tun0: flags=8051 mtu 1500 (problem + workaround applies both to tun and tap style devices) + * 2012-06-09 - this got fixed in one of the platform cleanups + TODO for IPv6 transport support ------------------------------- -[ Last updated: 11-Nov-2009. ] +[ Last updated: 10-Jun-2012. ] * All platforms: o mgmt console: as currently passes straight in_addr_t bits around @@ -175,14 +202,8 @@ TODO for IPv6 transport support listening IPv6 must permit incoming streams from allowed IPv4 peer, currently you need to pass eg: --remote ffff::1.2.3.4 - o do something with multi mode learn routes, for now just ignoring - ipv6 addresses seems the most sensible thing to do, because there's - no support for intra-tunnel ipv6 stuff. * win32: o find out about mapped addresses, as I can't make it work with bound at ::1 and connect to 127.0.0.1 -* N/A: - o this is ipv6 *endpoint* support, so don't expect "ifconfig6"-like - support in this patch diff --git a/openvpn/configure.ac b/openvpn/configure.ac index 913ace63..d3d974dc 100644 --- a/openvpn/configure.ac +++ b/openvpn/configure.ac @@ -193,6 +193,38 @@ AC_ARG_ENABLE( [enable_pf="yes"] ) +AC_ARG_ENABLE( + [plugin-auth-pam], + [AS_HELP_STRING([--disable-plugin-auth-pam], [disable auth-pam plugin @<:@default=platform specific@:>@])], + , + [ + case "$host" in + *-*-openbsd*) enable_plugin_auth_pam="no";; + *-mingw*) enable_plugin_auth_pam="no";; + *) enable_plugin_auth_pam="yes";; + esac + ] +) + +AC_ARG_ENABLE( + [plugin-down-root], + [AS_HELP_STRING([--disable-plugin-down-root], [disable down-root plugin @<:@default=platform specific@:>@])], + , + [ + case "$host" in + *-mingw*) enable_plugin_down_root="no";; + *) enable_plugin_down_root="yes";; + esac + ] +) + +AC_ARG_ENABLE( + [pam-dlopen], + [AS_HELP_STRING([--enable-pam-dlopen], [dlopen libpam @<:@default=no@:>@])], + , + [enable_pam_dlopen="no"] +) + AC_ARG_ENABLE( [strict], [AS_HELP_STRING([--enable-strict], [enable strict compiler warnings (debugging option) @<:@default=no@:>@])], @@ -228,6 +260,12 @@ AC_ARG_ENABLE( [enable_systemd="no"] ) +AC_ARG_WITH( + [special-build], + [AS_HELP_STRING([--with-special-build=STRING], [specify special build string])], + [test -n "${withval}" && AC_DEFINE_UNQUOTED([CONFIGURE_SPECIAL_BUILD], ["${withval}"], [special build string])] +) + AC_ARG_WITH( [mem-check], [AS_HELP_STRING([--with-mem-check=TYPE], [build with debug memory checking, TYPE=no|dmalloc|valgrind|ssl @<:@default=no@:>@])], @@ -252,6 +290,14 @@ AC_ARG_WITH( [with_crypto_library="openssl"] ) +AC_ARG_WITH( + [plugindir], + [AS_HELP_STRING([--with-plugindir], [plugin directory @<:@default=LIBDIR/openvpn@:>@])], + , + [with_plugindir="\$(libdir)/openvpn/plugins"] +) + + AC_DEFINE_UNQUOTED([TARGET_ALIAS], ["${host}"], [A string representing our host]) case "$host" in *-*-linux*) @@ -277,6 +323,7 @@ case "$host" in *-*-darwin*) AC_DEFINE([TARGET_DARWIN], [1], [Are we running on Mac OS X?]) AC_DEFINE_UNQUOTED([TARGET_PREFIX], ["M"], [Target prefix]) + have_tap_header="yes" dnl some Mac OS X tendering (we use vararg macros...) CPPFLAGS="$CPPFLAGS -no-cpp-precomp" ;; @@ -293,6 +340,7 @@ case "$host" in ;; *) AC_DEFINE_UNQUOTED([TARGET_PREFIX], ["X"], [Target prefix]) + have_tap_header="yes" ;; esac @@ -616,6 +664,16 @@ AC_CHECK_LIB( ) AC_SUBST([SELINUX_LIBS]) +AC_ARG_VAR([LIBPAM_CFLAGS], [C compiler flags for libpam]) +AC_ARG_VAR([LIBPAM_LIBS], [linker flags for libpam]) +if test -z "${LIBPAM_LIBS}"; then + AC_CHECK_LIB( + [pam], + [pam_start], + [LIBPAM_LIBS="-lpam"] + ) +fi + case "${with_mem_check}" in valgrind) AC_CHECK_HEADER( @@ -747,7 +805,7 @@ if test "${with_crypto_library}" = "polarssl" ; then #include ]], [[ -#if POLARSSL_VERSION_NUMBER <= 0x01010000 +#if POLARSSL_VERSION_NUMBER < 0x01010000 #error invalid version #endif ]] @@ -886,6 +944,9 @@ if test "${enable_plugins}" = "yes"; then OPTIONAL_DL_LIBS="${DL_LIBS}" AC_DEFINE([ENABLE_PLUGIN], [1], [Enable systemd support]) test "${enable_eurephia}" = "yes" && AC_DEFINE([ENABLE_EUREPHIA], [1], [Enable support for the eurephia plug-in]) +else + enable_plugin_auth_pam="no" + enable_plugin_down_root="no" fi if test "${enable_iproute2}" = "yes"; then @@ -937,6 +998,17 @@ if test "${WIN32}" = "yes"; then test -z "${MAN2HTML}" && AC_MSG_ERROR([man2html is required for win32]) fi +if test "${enable_plugin_auth_pam}" = "yes"; then + PLUGIN_AUTH_PAM_CFLAGS="${LIBPAM_CFLAGS}" + if test "${enable_pam_dlopen}" = "yes"; then + AC_DEFINE([USE_PAM_DLOPEN], [1], [dlopen libpam]) + PLUGIN_AUTH_PAM_LIBS="${DL_LIBS}" + else + test -z "${LIBPAM_LIBS}" && AC_MSG_ERROR([libpam required but missing]) + PLUGIN_AUTH_PAM_LIBS="${LIBPAM_LIBS}" + fi +fi + CONFIGURE_DEFINES="`set | grep '^enable_.*=' ; set | grep '^with_.*='`" AC_DEFINE_UNQUOTED([CONFIGURE_DEFINES], ["`echo ${CONFIGURE_DEFINES}`"], [Configuration settings]) @@ -959,10 +1031,17 @@ AC_SUBST([OPTIONAL_LZO_LIBS]) AC_SUBST([OPTIONAL_PKCS11_HELPER_CFLAGS]) AC_SUBST([OPTIONAL_PKCS11_HELPER_LIBS]) +AC_SUBST([PLUGIN_AUTH_PAM_CFLAGS]) +AC_SUBST([PLUGIN_AUTH_PAM_LIBS]) + AM_CONDITIONAL([WIN32], [test "${WIN32}" = "yes"]) AM_CONDITIONAL([GIT_CHECKOUT], [test "${GIT_CHECKOUT}" = "yes"]) +AM_CONDITIONAL([ENABLE_PLUGIN_AUTH_PAM], [test "${enable_plugin_auth_pam}" = "yes"]) +AM_CONDITIONAL([ENABLE_PLUGIN_DOWN_ROOT], [test "${enable_plugin_down_root}" = "yes"]) +plugindir="${with_plugindir}" sampledir="\$(docdir)/sample" +AC_SUBST([plugindir]) AC_SUBST([sampledir]) AC_CONFIG_FILES([ @@ -979,6 +1058,9 @@ AC_CONFIG_FILES([ src/compat/Makefile src/openvpn/Makefile src/openvpnserv/Makefile + src/plugins/Makefile + src/plugins/auth-pam/Makefile + src/plugins/down-root/Makefile tests/Makefile sample/Makefile doc/Makefile diff --git a/openvpn/distro/rpm/openvpn.spec.in b/openvpn/distro/rpm/openvpn.spec.in index 3c316bfb..20a8c890 100644 --- a/openvpn/distro/rpm/openvpn.spec.in +++ b/openvpn/distro/rpm/openvpn.spec.in @@ -82,13 +82,6 @@ Development support for OpenVPN. %define VENDOR %_vendor %endif -# -# Should we build the auth-pam module? -# - -%define build_auth_pam 1 -%{?without_pam:%define build_auth_pam 0} - # # Other definitions # @@ -108,20 +101,9 @@ Development support for OpenVPN. --docdir="%{_docdir}/%{name}-%{version}" \ %{?with_password_save:--enable-password-save} \ %{!?without_lzo:--enable-lzo} \ - %{?with_pkcs11:--enable-pkcs11} -%__make - -# Build down-root plugin -pushd src/plugins/down-root + %{?with_pkcs11:--enable-pkcs11} \ + %{?without_pam:--disable-plugin-auth-pam} %__make -popd - -# Build auth-pam plugin -%if %{build_auth_pam} -pushd src/plugins/auth-pam -%__make -popd -%endif # # Installation section @@ -143,29 +125,8 @@ popd # Install /etc/openvpn %__install -c -d -m 755 "%{buildroot}/etc/%{name}" -# -# Build /usr/share/openvpn -# - -%__mkdir_p %{buildroot}%{_datadir}/%{name} - -# -# Install the plugins -# - -%__mkdir_p "%{buildroot}%{_datadir}/%{name}/plugins/lib" - -for pi in auth-pam down-root; do - %__mv -f src/plugins/$pi/README src/plugins/README.$pi - if [ -e src/plugins/$pi/openvpn-$pi.so ]; then - %__install -c -m 755 src/plugins/$pi/openvpn-$pi.so "%{buildroot}%{_datadir}/openvpn/plugins/lib/openvpn-$pi.so" - fi -done - -%__mv -f src/plugins/README src/plugins/README.plugins - # Install extra %doc stuff -cp -r AUTHORS ChangeLog NEWS contrib/ sample/ src/plugins/README.* \ +cp -r AUTHORS ChangeLog NEWS contrib/ sample/ \ "%{buildroot}/%{_docdir}/%{name}-%{version}" # @@ -218,7 +179,7 @@ fi %defattr(-,root,root) %{_mandir} %{_sbindir}/%{name} -%{_datadir}/%{name} +%{_libdir}/%{name} %{_docdir}/%{name}-%{version} %dir /etc/%{name} %if "%{VENDOR}" == "SuSE" diff --git a/openvpn/doc/Makefile.am b/openvpn/doc/Makefile.am index 46687b29..d33e1edd 100644 --- a/openvpn/doc/Makefile.am +++ b/openvpn/doc/Makefile.am @@ -17,8 +17,11 @@ CLEANFILES = openvpn.8.html dist_doc_DATA = \ management-notes.txt +dist_noinst_DATA = \ + README.plugins + if WIN32 -dist_noinst_DATA = openvpn.8 +dist_noinst_DATA += openvpn.8 nodist_html_DATA = openvpn.8.html openvpn.8.html: $(srcdir)/openvpn.8 $(MAN2HTML) < $(srcdir)/openvpn.8 > openvpn.8.html diff --git a/openvpn/doc/README.plugins b/openvpn/doc/README.plugins new file mode 100644 index 00000000..6e490c5a --- /dev/null +++ b/openvpn/doc/README.plugins @@ -0,0 +1,47 @@ +OpenVPN Plugins +--------------- + +Starting with OpenVPN 2.0-beta17, compiled plugin modules are +supported on any *nix OS which includes libdl or on Windows. +One or more modules may be loaded into OpenVPN using +the --plugin directive, and each plugin module is capable of +intercepting any of the script callbacks which OpenVPN supports: + +(1) up +(2) down +(3) route-up +(4) ipchange +(5) tls-verify +(6) auth-user-pass-verify +(7) client-connect +(8) client-disconnect +(9) learn-address + +See the openvpn-plugin.h file in the top-level directory of the +OpenVPN source distribution for more detailed information +on the plugin interface. + +Included Plugins +---------------- + +auth-pam -- Authenticate using PAM and a split privilege + execution model which functions even if + root privileges or the execution environment + have been altered with --user/--group/--chroot. + Tested on Linux only. + +down-root -- Enable the running of down scripts with root privileges + even if --user/--group/--chroot have been used + to drop root privileges or change the execution + environment. Not applicable on Windows. + +examples -- A simple example that demonstrates a portable + plugin, i.e. one which can be built for *nix + or Windows from the same source. + +Building Plugins +---------------- + +cd to the top-level directory of a plugin, and use the +"make" command to build it. The examples plugin is +built using a build script, not a makefile. diff --git a/openvpn/doc/management-notes.txt b/openvpn/doc/management-notes.txt index 785eb881..a07a5142 100644 --- a/openvpn/doc/management-notes.txt +++ b/openvpn/doc/management-notes.txt @@ -719,6 +719,37 @@ use this command: remote SKIP +COMMAND -- proxy (OpenVPN 2.3 or higher) +-------------------------------------------- + +Provide proxy server host/port and flags in response to a >PROXY +notification (client only). Requires that the --management-query-proxy +directive is used. + + proxy TYPE HOST PORT ["nct"] + +The "proxy" command must only be given in response to a >PROXY +notification. Use the "nct" flag if you only want to allow +non-cleartext auth with the proxy server. The following >PROXY +notification indicates that the client config file would ordinarily +connect to the first --remote configured, vpn.example.com using TCP: + + >PROXY:1,TCP,vpn.example.com + +Now, suppose we want to connect to the remote host using the proxy server +proxy.intranet port 8080 with secure authentication only, if required. +After receiving the above notification, use this command: + + proxy HTTP proxy.intranet 8080 nct + +You can also use the SOCKS keyword to pass a SOCKS server address, like: + + proxy SOCKS fe00::1 1080 + +To accept connecting to the host and port directly, use this command: + + proxy NONE + OUTPUT FORMAT ------------- diff --git a/openvpn/doc/openvpn.8 b/openvpn/doc/openvpn.8 index f420d584..56be29ec 100644 --- a/openvpn/doc/openvpn.8 +++ b/openvpn/doc/openvpn.8 @@ -482,18 +482,6 @@ as the number of retries of connection attempt (default=infinite). .\"********************************************************* .TP -.B \-\-auto-proxy -Try to sense HTTP or SOCKS proxy settings automatically. -If no settings are present, a direct connection will be attempted. -If both HTTP and SOCKS settings are present, HTTP will be preferred. -If the HTTP proxy server requires a password, it will be queried from -stdin or the management interface. If the underlying OS doesn't support an API for -returning proxy settings, a direct connection will be attempted. -Currently, only Windows clients support this option via the -InternetQueryOption API. -This option exists in OpenVPN 2.1 or higher. -.\"********************************************************* -.TP .B \-\-show-proxy-settings Show sensed HTTP or SOCKS proxy settings. Currently, only Windows clients support this option. @@ -2458,6 +2446,12 @@ for inputs which ordinarily would have been queried from the console. .\"********************************************************* .TP +.B \-\-management-query-proxy +Query management channel for proxy server information for a specific +.B \-\-remote +(client-only). +.\"********************************************************* +.TP .B \-\-management-query-remote Allow management interface to override .B \-\-remote diff --git a/openvpn/msvc-build.bat b/openvpn/msvc-build.bat index 01417d1b..fd6d5588 100644 --- a/openvpn/msvc-build.bat +++ b/openvpn/msvc-build.bat @@ -4,6 +4,7 @@ rem Copyright (C) 2008-2012 Alon Bar-Lev @rem this stupid command needed for SetEnv.cmd to operate setlocal ENABLEDELAYEDEXPANSION +cd /d %0\.. call msvc-env.bat set PLATFORMS=Win32 diff --git a/openvpn/msvc-dev.bat b/openvpn/msvc-dev.bat index 4dac1720..dbd7be07 100644 --- a/openvpn/msvc-dev.bat +++ b/openvpn/msvc-dev.bat @@ -1,7 +1,7 @@ @echo off setlocal -cd %0\.. +cd /d %0\.. call msvc-env.bat if exist "%VSHOME%\Common7\IDE\VCExpress.exe" ( diff --git a/openvpn/msvc-env.bat b/openvpn/msvc-env.bat index 3c9eb5bf..2dd0f00d 100644 --- a/openvpn/msvc-env.bat +++ b/openvpn/msvc-env.bat @@ -1,7 +1,5 @@ @echo off -cd %0\.. - rem Put your own settings at msvc-env-local.bat if exist msvc-env-local.bat call msvc-env-local.bat diff --git a/openvpn/sample/Makefile.am b/openvpn/sample/Makefile.am index 8e35bfc9..be30c88a 100644 --- a/openvpn/sample/Makefile.am +++ b/openvpn/sample/Makefile.am @@ -13,6 +13,7 @@ MAINTAINERCLEANFILES = \ $(srcdir)/Makefile.in EXTRA_DIST = \ + sample-plugins \ sample-config-files \ sample-windows \ sample-keys \ diff --git a/openvpn/sample/sample-plugins/defer/README b/openvpn/sample/sample-plugins/defer/README new file mode 100644 index 00000000..d8990f8b --- /dev/null +++ b/openvpn/sample/sample-plugins/defer/README @@ -0,0 +1,16 @@ +OpenVPN plugin examples. + +Examples provided: + +simple.c -- using the --auth-user-pass-verify callback, + test deferred authentication. + +To build: + + ./build simple (Linux/BSD/etc.) + ./winbuild simple (MinGW on Windows) + +To use in OpenVPN, add to config file: + + plugin simple.so (Linux/BSD/etc.) + plugin simple.dll (MinGW on Windows) diff --git a/openvpn/sample/sample-plugins/defer/build b/openvpn/sample/sample-plugins/defer/build new file mode 100755 index 00000000..0612c080 --- /dev/null +++ b/openvpn/sample/sample-plugins/defer/build @@ -0,0 +1,15 @@ +#!/bin/sh + +# +# Build an OpenVPN plugin module on *nix. The argument should +# be the base name of the C source file (without the .c). +# + +# This directory is where we will look for openvpn-plugin.h +CPPFLAGS="${CPPFLAGS:--I../../../include}" + +CC="${CC:-gcc}" +CFLAGS="${CFLAGS:--O2 -Wall -g}" + +$CC $CPPFLAGS $CFLAGS -fPIC -c $1.c && \ +$CC $CFLAGS -fPIC -shared ${LDFLAS} -Wl,-soname,$1.so -o $1.so $1.o -lc diff --git a/openvpn/sample/sample-plugins/defer/simple.c b/openvpn/sample/sample-plugins/defer/simple.c new file mode 100644 index 00000000..65398657 --- /dev/null +++ b/openvpn/sample/sample-plugins/defer/simple.c @@ -0,0 +1,305 @@ +/* + * OpenVPN -- An application to securely tunnel IP networks + * over a single TCP/UDP port, with support for SSL/TLS-based + * session authentication and key exchange, + * packet encryption, packet authentication, and + * packet compression. + * + * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. + * + * 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 (see the file COPYING included with this + * distribution); if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +/* + * This file implements a simple OpenVPN plugin module which + * will test deferred authentication and packet filtering. + * + * Will run on Windows or *nix. + * + * Sample usage: + * + * setenv test_deferred_auth 20 + * setenv test_packet_filter 10 + * plugin plugin/defer/simple.so + * + * This will enable deferred authentication to occur 20 + * seconds after the normal TLS authentication process, + * and will cause a packet filter file to be generated 10 + * seconds after the initial TLS negotiation, using + * {common-name}.pf as the source. + * + * Sample packet filter configuration: + * + * [CLIENTS DROP] + * +otherclient + * [SUBNETS DROP] + * +10.0.0.0/8 + * -10.10.0.8 + * [END] + * + * See the README file for build instructions. + */ + +#include +#include +#include + +#include "openvpn-plugin.h" + +/* bool definitions */ +#define bool int +#define true 1 +#define false 0 + +/* + * Our context, where we keep our state. + */ + +struct plugin_context { + int test_deferred_auth; + int test_packet_filter; +}; + +struct plugin_per_client_context { + int n_calls; + bool generated_pf_file; +}; + +/* + * Given an environmental variable name, search + * the envp array for its value, returning it + * if found or NULL otherwise. + */ +static const char * +get_env (const char *name, const char *envp[]) +{ + if (envp) + { + int i; + const int namelen = strlen (name); + for (i = 0; envp[i]; ++i) + { + if (!strncmp (envp[i], name, namelen)) + { + const char *cp = envp[i] + namelen; + if (*cp == '=') + return cp + 1; + } + } + } + return NULL; +} + +/* used for safe printf of possible NULL strings */ +static const char * +np (const char *str) +{ + if (str) + return str; + else + return "[NULL]"; +} + +static int +atoi_null0 (const char *str) +{ + if (str) + return atoi (str); + else + return 0; +} + +OPENVPN_EXPORT openvpn_plugin_handle_t +openvpn_plugin_open_v1 (unsigned int *type_mask, const char *argv[], const char *envp[]) +{ + struct plugin_context *context; + + printf ("FUNC: openvpn_plugin_open_v1\n"); + + /* + * Allocate our context + */ + context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); + + context->test_deferred_auth = atoi_null0 (get_env ("test_deferred_auth", envp)); + printf ("TEST_DEFERRED_AUTH %d\n", context->test_deferred_auth); + + context->test_packet_filter = atoi_null0 (get_env ("test_packet_filter", envp)); + printf ("TEST_PACKET_FILTER %d\n", context->test_packet_filter); + + /* + * Which callbacks to intercept. + */ + *type_mask = + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_UP) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_DOWN) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ROUTE_UP) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_IPCHANGE) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_VERIFY) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_CONNECT_V2) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_DISCONNECT) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_LEARN_ADDRESS) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_FINAL) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ENABLE_PF); + + return (openvpn_plugin_handle_t) context; +} + +static int +auth_user_pass_verify (struct plugin_context *context, struct plugin_per_client_context *pcc, const char *argv[], const char *envp[]) +{ + if (context->test_deferred_auth) + { + /* get username/password from envp string array */ + const char *username = get_env ("username", envp); + const char *password = get_env ("password", envp); + + /* get auth_control_file filename from envp string array*/ + const char *auth_control_file = get_env ("auth_control_file", envp); + + printf ("DEFER u='%s' p='%s' acf='%s'\n", + np(username), + np(password), + np(auth_control_file)); + + /* Authenticate asynchronously in n seconds */ + if (auth_control_file) + { + char buf[256]; + int auth = 2; + sscanf (username, "%d", &auth); + snprintf (buf, sizeof(buf), "( sleep %d ; echo AUTH %s %d ; echo %d >%s ) &", + context->test_deferred_auth, + auth_control_file, + auth, + pcc->n_calls < auth, + auth_control_file); + printf ("%s\n", buf); + system (buf); + pcc->n_calls++; + return OPENVPN_PLUGIN_FUNC_DEFERRED; + } + else + return OPENVPN_PLUGIN_FUNC_ERROR; + } + else + return OPENVPN_PLUGIN_FUNC_SUCCESS; +} + +static int +tls_final (struct plugin_context *context, struct plugin_per_client_context *pcc, const char *argv[], const char *envp[]) +{ + if (context->test_packet_filter) + { + if (!pcc->generated_pf_file) + { + const char *pff = get_env ("pf_file", envp); + const char *cn = get_env ("username", envp); + if (pff && cn) + { + char buf[256]; + snprintf (buf, sizeof(buf), "( sleep %d ; echo PF %s/%s ; cp \"%s.pf\" \"%s\" ) &", + context->test_packet_filter, cn, pff, cn, pff); + printf ("%s\n", buf); + system (buf); + pcc->generated_pf_file = true; + return OPENVPN_PLUGIN_FUNC_SUCCESS; + } + else + return OPENVPN_PLUGIN_FUNC_ERROR; + } + else + return OPENVPN_PLUGIN_FUNC_ERROR; + } + else + return OPENVPN_PLUGIN_FUNC_SUCCESS; +} + +OPENVPN_EXPORT int +openvpn_plugin_func_v2 (openvpn_plugin_handle_t handle, + const int type, + const char *argv[], + const char *envp[], + void *per_client_context, + struct openvpn_plugin_string_list **return_list) +{ + struct plugin_context *context = (struct plugin_context *) handle; + struct plugin_per_client_context *pcc = (struct plugin_per_client_context *) per_client_context; + switch (type) + { + case OPENVPN_PLUGIN_UP: + printf ("OPENVPN_PLUGIN_UP\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_DOWN: + printf ("OPENVPN_PLUGIN_DOWN\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_ROUTE_UP: + printf ("OPENVPN_PLUGIN_ROUTE_UP\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_IPCHANGE: + printf ("OPENVPN_PLUGIN_IPCHANGE\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_TLS_VERIFY: + printf ("OPENVPN_PLUGIN_TLS_VERIFY\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY: + printf ("OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY\n"); + return auth_user_pass_verify (context, pcc, argv, envp); + case OPENVPN_PLUGIN_CLIENT_CONNECT_V2: + printf ("OPENVPN_PLUGIN_CLIENT_CONNECT_V2\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_CLIENT_DISCONNECT: + printf ("OPENVPN_PLUGIN_CLIENT_DISCONNECT\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_LEARN_ADDRESS: + printf ("OPENVPN_PLUGIN_LEARN_ADDRESS\n"); + return OPENVPN_PLUGIN_FUNC_SUCCESS; + case OPENVPN_PLUGIN_TLS_FINAL: + printf ("OPENVPN_PLUGIN_TLS_FINAL\n"); + return tls_final (context, pcc, argv, envp); + case OPENVPN_PLUGIN_ENABLE_PF: + printf ("OPENVPN_PLUGIN_ENABLE_PF\n"); + if (context->test_packet_filter) + return OPENVPN_PLUGIN_FUNC_SUCCESS; + else + return OPENVPN_PLUGIN_FUNC_ERROR; + default: + printf ("OPENVPN_PLUGIN_?\n"); + return OPENVPN_PLUGIN_FUNC_ERROR; + } +} + +OPENVPN_EXPORT void * +openvpn_plugin_client_constructor_v1 (openvpn_plugin_handle_t handle) +{ + printf ("FUNC: openvpn_plugin_client_constructor_v1\n"); + return calloc (1, sizeof (struct plugin_per_client_context)); +} + +OPENVPN_EXPORT void +openvpn_plugin_client_destructor_v1 (openvpn_plugin_handle_t handle, void *per_client_context) +{ + printf ("FUNC: openvpn_plugin_client_destructor_v1\n"); + free (per_client_context); +} + +OPENVPN_EXPORT void +openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) +{ + struct plugin_context *context = (struct plugin_context *) handle; + printf ("FUNC: openvpn_plugin_close_v1\n"); + free (context); +} diff --git a/openvpn/sample/sample-plugins/defer/simple.def b/openvpn/sample/sample-plugins/defer/simple.def new file mode 100755 index 00000000..a87507d1 --- /dev/null +++ b/openvpn/sample/sample-plugins/defer/simple.def @@ -0,0 +1,6 @@ +LIBRARY OpenVPN_PLUGIN_SAMPLE +DESCRIPTION "Sample OpenVPN plug-in module." +EXPORTS + openvpn_plugin_open_v1 @1 + openvpn_plugin_func_v1 @2 + openvpn_plugin_close_v1 @3 diff --git a/openvpn/sample/sample-plugins/defer/winbuild b/openvpn/sample/sample-plugins/defer/winbuild new file mode 100755 index 00000000..82927d96 --- /dev/null +++ b/openvpn/sample/sample-plugins/defer/winbuild @@ -0,0 +1,18 @@ +# +# Build an OpenVPN plugin module on Windows/MinGW. +# The argument should be the base name of the C source file +# (without the .c). +# + +# This directory is where we will look for openvpn-plugin.h +INCLUDE="-I../../../build" + +CC_FLAGS="-O2 -Wall" + +gcc -DBUILD_DLL $CC_FLAGS $INCLUDE -c $1.c +gcc --disable-stdcall-fixup -mdll -DBUILD_DLL -o junk.tmp -Wl,--base-file,base.tmp $1.o +rm junk.tmp +dlltool --dllname $1.dll --base-file base.tmp --output-exp temp.exp --input-def $1.def +rm base.tmp +gcc --enable-stdcall-fixup -mdll -DBUILD_DLL -o $1.dll $1.o -Wl,temp.exp +rm temp.exp diff --git a/openvpn/sample/sample-plugins/log/build b/openvpn/sample/sample-plugins/log/build new file mode 100755 index 00000000..bbb05f7c --- /dev/null +++ b/openvpn/sample/sample-plugins/log/build @@ -0,0 +1,15 @@ +#!/bin/sh + +# +# Build an OpenVPN plugin module on *nix. The argument should +# be the base name of the C source file (without the .c). +# + +# This directory is where we will look for openvpn-plugin.h +CPPFLAGS="${CPPFLAGS:--I../../..}" + +CC="${CC:-gcc}" +CFLAGS="${CFLAGS:--O2 -Wall -g}" + +$CC $CPPFLAGS $CFLAGS -fPIC -c $1.c && \ +$CC $CFLAGS -fPIC -shared $LDFLAGS -Wl,-soname,$1.so -o $1.so $1.o -lc diff --git a/openvpn/sample/sample-plugins/log/log.c b/openvpn/sample/sample-plugins/log/log.c new file mode 100644 index 00000000..1cc4650e --- /dev/null +++ b/openvpn/sample/sample-plugins/log/log.c @@ -0,0 +1,184 @@ +/* + * OpenVPN -- An application to securely tunnel IP networks + * over a single TCP/UDP port, with support for SSL/TLS-based + * session authentication and key exchange, + * packet encryption, packet authentication, and + * packet compression. + * + * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. + * + * 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 (see the file COPYING included with this + * distribution); if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +/* + * This plugin is similar to simple.c, except it also logs extra information + * to stdout for every plugin method called by OpenVPN. + * + * See the README file for build instructions. + */ + +#include +#include +#include + +#include "openvpn-plugin.h" + +/* + * Our context, where we keep our state. + */ +struct plugin_context { + const char *username; + const char *password; +}; + +/* + * Given an environmental variable name, search + * the envp array for its value, returning it + * if found or NULL otherwise. + */ +static const char * +get_env (const char *name, const char *envp[]) +{ + if (envp) + { + int i; + const int namelen = strlen (name); + for (i = 0; envp[i]; ++i) + { + if (!strncmp (envp[i], name, namelen)) + { + const char *cp = envp[i] + namelen; + if (*cp == '=') + return cp + 1; + } + } + } + return NULL; +} + +OPENVPN_EXPORT openvpn_plugin_handle_t +openvpn_plugin_open_v1 (unsigned int *type_mask, const char *argv[], const char *envp[]) +{ + struct plugin_context *context; + + /* + * Allocate our context + */ + context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); + + /* + * Set the username/password we will require. + */ + context->username = "foo"; + context->password = "bar"; + + /* + * Which callbacks to intercept. + */ + *type_mask = + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_UP) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_DOWN) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ROUTE_UP) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_IPCHANGE) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_VERIFY) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_CONNECT_V2) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_DISCONNECT) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_LEARN_ADDRESS) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_FINAL); + + return (openvpn_plugin_handle_t) context; +} + +void +show (const int type, const char *argv[], const char *envp[]) +{ + size_t i; + switch (type) + { + case OPENVPN_PLUGIN_UP: + printf ("OPENVPN_PLUGIN_UP\n"); + break; + case OPENVPN_PLUGIN_DOWN: + printf ("OPENVPN_PLUGIN_DOWN\n"); + break; + case OPENVPN_PLUGIN_ROUTE_UP: + printf ("OPENVPN_PLUGIN_ROUTE_UP\n"); + break; + case OPENVPN_PLUGIN_IPCHANGE: + printf ("OPENVPN_PLUGIN_IPCHANGE\n"); + break; + case OPENVPN_PLUGIN_TLS_VERIFY: + printf ("OPENVPN_PLUGIN_TLS_VERIFY\n"); + break; + case OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY: + printf ("OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY\n"); + break; + case OPENVPN_PLUGIN_CLIENT_CONNECT_V2: + printf ("OPENVPN_PLUGIN_CLIENT_CONNECT_V2\n"); + break; + case OPENVPN_PLUGIN_CLIENT_DISCONNECT: + printf ("OPENVPN_PLUGIN_CLIENT_DISCONNECT\n"); + break; + case OPENVPN_PLUGIN_LEARN_ADDRESS: + printf ("OPENVPN_PLUGIN_LEARN_ADDRESS\n"); + break; + case OPENVPN_PLUGIN_TLS_FINAL: + printf ("OPENVPN_PLUGIN_TLS_FINAL\n"); + break; + default: + printf ("OPENVPN_PLUGIN_?\n"); + break; + } + + printf ("ARGV\n"); + for (i = 0; argv[i] != NULL; ++i) + printf ("%d '%s'\n", (int)i, argv[i]); + + printf ("ENVP\n"); + for (i = 0; envp[i] != NULL; ++i) + printf ("%d '%s'\n", (int)i, envp[i]); +} + +OPENVPN_EXPORT int +openvpn_plugin_func_v1 (openvpn_plugin_handle_t handle, const int type, const char *argv[], const char *envp[]) +{ + struct plugin_context *context = (struct plugin_context *) handle; + + show (type, argv, envp); + + /* check entered username/password against what we require */ + if (type == OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) + { + /* get username/password from envp string array */ + const char *username = get_env ("username", envp); + const char *password = get_env ("password", envp); + + if (username && !strcmp (username, context->username) + && password && !strcmp (password, context->password)) + return OPENVPN_PLUGIN_FUNC_SUCCESS; + else + return OPENVPN_PLUGIN_FUNC_ERROR; + } + else + return OPENVPN_PLUGIN_FUNC_SUCCESS; +} + +OPENVPN_EXPORT void +openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) +{ + struct plugin_context *context = (struct plugin_context *) handle; + free (context); +} diff --git a/openvpn/sample/sample-plugins/log/log_v3.c b/openvpn/sample/sample-plugins/log/log_v3.c new file mode 100644 index 00000000..742c7568 --- /dev/null +++ b/openvpn/sample/sample-plugins/log/log_v3.c @@ -0,0 +1,247 @@ +/* + * OpenVPN -- An application to securely tunnel IP networks + * over a single TCP/UDP port, with support for SSL/TLS-based + * session authentication and key exchange, + * packet encryption, packet authentication, and + * packet compression. + * + * Copyright (C) 2002-2009 OpenVPN Technologies, Inc. + * Copyright (C) 2010 David Sommerseth + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. + * + * 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 (see the file COPYING included with this + * distribution); if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +/* + * This plugin is similar to simple.c, except it also logs extra information + * to stdout for every plugin method called by OpenVPN. The only difference + * between this (log_v3.c) and log.c is that this module uses the v3 plug-in + * API. + * + * See the README file for build instructions. + */ + +#include +#include +#include + +#define ENABLE_SSL + +#include "openvpn-plugin.h" + +/* + * Our context, where we keep our state. + */ +struct plugin_context { + const char *username; + const char *password; +}; + +/* + * Given an environmental variable name, search + * the envp array for its value, returning it + * if found or NULL otherwise. + */ +static const char * +get_env (const char *name, const char *envp[]) +{ + if (envp) + { + int i; + const int namelen = strlen (name); + for (i = 0; envp[i]; ++i) + { + if (!strncmp (envp[i], name, namelen)) + { + const char *cp = envp[i] + namelen; + if (*cp == '=') + return cp + 1; + } + } + } + return NULL; +} + +OPENVPN_EXPORT int +openvpn_plugin_open_v3 (const int v3structver, + struct openvpn_plugin_args_open_in const *args, + struct openvpn_plugin_args_open_return *ret) +{ + struct plugin_context *context = NULL; + + /* Check that we are API compatible */ + if( v3structver != OPENVPN_PLUGINv3_STRUCTVER ) { + return OPENVPN_PLUGIN_FUNC_ERROR; + } + + /* Which callbacks to intercept. */ + ret->type_mask = + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_UP) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_DOWN) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ROUTE_UP) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_IPCHANGE) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_VERIFY) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_CONNECT_V2) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_DISCONNECT) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_LEARN_ADDRESS) | + OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_FINAL); + + + /* Allocate our context */ + context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); + + /* Set the username/password we will require. */ + context->username = "foo"; + context->password = "bar"; + + /* Point the global context handle to our newly created context */ + ret->handle = (void *) context; + + return OPENVPN_PLUGIN_FUNC_SUCCESS; +} + +void +show (const int type, const char *argv[], const char *envp[]) +{ + size_t i; + switch (type) + { + case OPENVPN_PLUGIN_UP: + printf ("OPENVPN_PLUGIN_UP\n"); + break; + case OPENVPN_PLUGIN_DOWN: + printf ("OPENVPN_PLUGIN_DOWN\n"); + break; + case OPENVPN_PLUGIN_ROUTE_UP: + printf ("OPENVPN_PLUGIN_ROUTE_UP\n"); + break; + case OPENVPN_PLUGIN_IPCHANGE: + printf ("OPENVPN_PLUGIN_IPCHANGE\n"); + break; + case OPENVPN_PLUGIN_TLS_VERIFY: + printf ("OPENVPN_PLUGIN_TLS_VERIFY\n"); + break; + case OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY: + printf ("OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY\n"); + break; + case OPENVPN_PLUGIN_CLIENT_CONNECT_V2: + printf ("OPENVPN_PLUGIN_CLIENT_CONNECT_V2\n"); + break; + case OPENVPN_PLUGIN_CLIENT_DISCONNECT: + printf ("OPENVPN_PLUGIN_CLIENT_DISCONNECT\n"); + break; + case OPENVPN_PLUGIN_LEARN_ADDRESS: + printf ("OPENVPN_PLUGIN_LEARN_ADDRESS\n"); + break; + case OPENVPN_PLUGIN_TLS_FINAL: + printf ("OPENVPN_PLUGIN_TLS_FINAL\n"); + break; + default: + printf ("OPENVPN_PLUGIN_?\n"); + break; + } + + printf ("ARGV\n"); + for (i = 0; argv[i] != NULL; ++i) + printf ("%d '%s'\n", (int)i, argv[i]); + + printf ("ENVP\n"); + for (i = 0; envp[i] != NULL; ++i) + printf ("%d '%s'\n", (int)i, envp[i]); +} + +static void +x509_print_info (X509 *x509crt) +{ + int i, n; + int fn_nid; + ASN1_OBJECT *fn; + ASN1_STRING *val; + X509_NAME *x509_name; + X509_NAME_ENTRY *ent; + const char *objbuf; + unsigned char *buf; + + x509_name = X509_get_subject_name (x509crt); + n = X509_NAME_entry_count (x509_name); + for (i = 0; i < n; ++i) + { + ent = X509_NAME_get_entry (x509_name, i); + if (!ent) + continue; + fn = X509_NAME_ENTRY_get_object (ent); + if (!fn) + continue; + val = X509_NAME_ENTRY_get_data (ent); + if (!val) + continue; + fn_nid = OBJ_obj2nid (fn); + if (fn_nid == NID_undef) + continue; + objbuf = OBJ_nid2sn (fn_nid); + if (!objbuf) + continue; + buf = (unsigned char *)1; /* bug in OpenSSL 0.9.6b ASN1_STRING_to_UTF8 requires this workaround */ + if (ASN1_STRING_to_UTF8 (&buf, val) <= 0) + continue; + + printf("X509 %s: %s\n", objbuf, (char *)buf); + OPENSSL_free (buf); + } +} + + + +OPENVPN_EXPORT int +openvpn_plugin_func_v3 (const int version, + struct openvpn_plugin_args_func_in const *args, + struct openvpn_plugin_args_func_return *retptr) +{ + struct plugin_context *context = (struct plugin_context *) args->handle; + + printf("\nopenvpn_plugin_func_v3() :::::>> "); + show (args->type, args->argv, args->envp); + + /* Dump some X509 information if we're in the TLS_VERIFY phase */ + if ((args->type == OPENVPN_PLUGIN_TLS_VERIFY) && args->current_cert ) { + printf("---- X509 Subject information ----\n"); + printf("Certificate depth: %i\n", args->current_cert_depth); + x509_print_info(args->current_cert); + printf("----------------------------------\n"); + } + + /* check entered username/password against what we require */ + if (args->type == OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) + { + /* get username/password from envp string array */ + const char *username = get_env ("username", args->envp); + const char *password = get_env ("password", args->envp); + + if (username && !strcmp (username, context->username) + && password && !strcmp (password, context->password)) + return OPENVPN_PLUGIN_FUNC_SUCCESS; + else + return OPENVPN_PLUGIN_FUNC_ERROR; + } + else + return OPENVPN_PLUGIN_FUNC_SUCCESS; +} + +OPENVPN_EXPORT void +openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) +{ + struct plugin_context *context = (struct plugin_context *) handle; + free (context); +} diff --git a/openvpn/sample/sample-plugins/log/winbuild b/openvpn/sample/sample-plugins/log/winbuild new file mode 100755 index 00000000..decf05f8 --- /dev/null +++ b/openvpn/sample/sample-plugins/log/winbuild @@ -0,0 +1,18 @@ +# +# Build an OpenVPN plugin module on Windows/MinGW. +# The argument should be the base name of the C source file +# (without the .c). +# + +# This directory is where we will look for openvpn-plugin.h +INCLUDE="-I../../../include" + +CC_FLAGS="-O2 -Wall" + +gcc -DBUILD_DLL $CC_FLAGS $INCLUDE -c $1.c +gcc --disable-stdcall-fixup -mdll -DBUILD_DLL -o junk.tmp -Wl,--base-file,base.tmp $1.o +rm junk.tmp +dlltool --dllname $1.dll --base-file base.tmp --output-exp temp.exp --input-def $1.def +rm base.tmp +gcc --enable-stdcall-fixup -mdll -DBUILD_DLL -o $1.dll $1.o -Wl,temp.exp +rm temp.exp diff --git a/openvpn/sample/sample-plugins/simple/README b/openvpn/sample/sample-plugins/simple/README new file mode 100644 index 00000000..4400cd30 --- /dev/null +++ b/openvpn/sample/sample-plugins/simple/README @@ -0,0 +1,16 @@ +OpenVPN plugin examples. + +Examples provided: + +simple.c -- using the --auth-user-pass-verify callback, verify + that the username/password is "foo"/"bar". + +To build: + + ./build simple (Linux/BSD/etc.) + ./winbuild simple (MinGW on Windows) + +To use in OpenVPN, add to config file: + + plugin simple.so (Linux/BSD/etc.) + plugin simple.dll (MinGW on Windows) diff --git a/openvpn/sample/sample-plugins/simple/build b/openvpn/sample/sample-plugins/simple/build new file mode 100755 index 00000000..bbb05f7c --- /dev/null +++ b/openvpn/sample/sample-plugins/simple/build @@ -0,0 +1,15 @@ +#!/bin/sh + +# +# Build an OpenVPN plugin module on *nix. The argument should +# be the base name of the C source file (without the .c). +# + +# This directory is where we will look for openvpn-plugin.h +CPPFLAGS="${CPPFLAGS:--I../../..}" + +CC="${CC:-gcc}" +CFLAGS="${CFLAGS:--O2 -Wall -g}" + +$CC $CPPFLAGS $CFLAGS -fPIC -c $1.c && \ +$CC $CFLAGS -fPIC -shared $LDFLAGS -Wl,-soname,$1.so -o $1.so $1.o -lc diff --git a/openvpn/sample/sample-plugins/simple/simple.c b/openvpn/sample/sample-plugins/simple/simple.c new file mode 100644 index 00000000..f26d89f6 --- /dev/null +++ b/openvpn/sample/sample-plugins/simple/simple.c @@ -0,0 +1,120 @@ +/* + * OpenVPN -- An application to securely tunnel IP networks + * over a single TCP/UDP port, with support for SSL/TLS-based + * session authentication and key exchange, + * packet encryption, packet authentication, and + * packet compression. + * + * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. + * + * 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 (see the file COPYING included with this + * distribution); if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +/* + * This file implements a simple OpenVPN plugin module which + * will examine the username/password provided by a client, + * and make an accept/deny determination. Will run + * on Windows or *nix. + * + * See the README file for build instructions. + */ + +#include +#include +#include + +#include "openvpn-plugin.h" + +/* + * Our context, where we keep our state. + */ +struct plugin_context { + const char *username; + const char *password; +}; + +/* + * Given an environmental variable name, search + * the envp array for its value, returning it + * if found or NULL otherwise. + */ +static const char * +get_env (const char *name, const char *envp[]) +{ + if (envp) + { + int i; + const int namelen = strlen (name); + for (i = 0; envp[i]; ++i) + { + if (!strncmp (envp[i], name, namelen)) + { + const char *cp = envp[i] + namelen; + if (*cp == '=') + return cp + 1; + } + } + } + return NULL; +} + +OPENVPN_EXPORT openvpn_plugin_handle_t +openvpn_plugin_open_v1 (unsigned int *type_mask, const char *argv[], const char *envp[]) +{ + struct plugin_context *context; + + /* + * Allocate our context + */ + context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); + + /* + * Set the username/password we will require. + */ + context->username = "foo"; + context->password = "bar"; + + /* + * We are only interested in intercepting the + * --auth-user-pass-verify callback. + */ + *type_mask = OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY); + + return (openvpn_plugin_handle_t) context; +} + +OPENVPN_EXPORT int +openvpn_plugin_func_v1 (openvpn_plugin_handle_t handle, const int type, const char *argv[], const char *envp[]) +{ + struct plugin_context *context = (struct plugin_context *) handle; + + /* get username/password from envp string array */ + const char *username = get_env ("username", envp); + const char *password = get_env ("password", envp); + + /* check entered username/password against what we require */ + if (username && !strcmp (username, context->username) + && password && !strcmp (password, context->password)) + return OPENVPN_PLUGIN_FUNC_SUCCESS; + else + return OPENVPN_PLUGIN_FUNC_ERROR; +} + +OPENVPN_EXPORT void +openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) +{ + struct plugin_context *context = (struct plugin_context *) handle; + free (context); +} diff --git a/openvpn/sample/sample-plugins/simple/simple.def b/openvpn/sample/sample-plugins/simple/simple.def new file mode 100755 index 00000000..a87507d1 --- /dev/null +++ b/openvpn/sample/sample-plugins/simple/simple.def @@ -0,0 +1,6 @@ +LIBRARY OpenVPN_PLUGIN_SAMPLE +DESCRIPTION "Sample OpenVPN plug-in module." +EXPORTS + openvpn_plugin_open_v1 @1 + openvpn_plugin_func_v1 @2 + openvpn_plugin_close_v1 @3 diff --git a/openvpn/sample/sample-plugins/simple/winbuild b/openvpn/sample/sample-plugins/simple/winbuild new file mode 100755 index 00000000..decf05f8 --- /dev/null +++ b/openvpn/sample/sample-plugins/simple/winbuild @@ -0,0 +1,18 @@ +# +# Build an OpenVPN plugin module on Windows/MinGW. +# The argument should be the base name of the C source file +# (without the .c). +# + +# This directory is where we will look for openvpn-plugin.h +INCLUDE="-I../../../include" + +CC_FLAGS="-O2 -Wall" + +gcc -DBUILD_DLL $CC_FLAGS $INCLUDE -c $1.c +gcc --disable-stdcall-fixup -mdll -DBUILD_DLL -o junk.tmp -Wl,--base-file,base.tmp $1.o +rm junk.tmp +dlltool --dllname $1.dll --base-file base.tmp --output-exp temp.exp --input-def $1.def +rm base.tmp +gcc --enable-stdcall-fixup -mdll -DBUILD_DLL -o $1.dll $1.o -Wl,temp.exp +rm temp.exp diff --git a/openvpn/src/Makefile.am b/openvpn/src/Makefile.am index b8949770..c04468a5 100644 --- a/openvpn/src/Makefile.am +++ b/openvpn/src/Makefile.am @@ -12,7 +12,4 @@ MAINTAINERCLEANFILES = \ $(srcdir)/Makefile.in -EXTRA_DIST = \ - plugins - -SUBDIRS = compat openvpn openvpnserv +SUBDIRS = compat openvpn openvpnserv plugins diff --git a/openvpn/src/openvpn/Makefile.am b/openvpn/src/openvpn/Makefile.am index d090d673..5d38628d 100644 --- a/openvpn/src/openvpn/Makefile.am +++ b/openvpn/src/openvpn/Makefile.am @@ -27,6 +27,10 @@ AM_CFLAGS = \ $(OPTIONAL_CRYPTO_CFLAGS) \ $(OPTIONAL_LZO_CFLAGS) \ $(OPTIONAL_PKCS11_HELPER_CFLAGS) +if WIN32 +# we want unicode entry point but not the macro +AM_CFLAGS += -municode -UUNICODE +endif sbin_PROGRAMS = openvpn @@ -118,5 +122,5 @@ openvpn_LDADD = \ $(OPTIONAL_DL_LIBS) if WIN32 openvpn_SOURCES += openvpn_win32_resources.rc -openvpn_LDADD += -lgdi32 -lws2_32 -lwininet -lcrypt32 -liphlpapi -lwinmm -lshell32 +openvpn_LDADD += -lgdi32 -lws2_32 -lwininet -lcrypt32 -liphlpapi -lwinmm endif diff --git a/openvpn/src/openvpn/common.h b/openvpn/src/openvpn/common.h index de2d6092..dd2c83f4 100644 --- a/openvpn/src/openvpn/common.h +++ b/openvpn/src/openvpn/common.h @@ -95,9 +95,7 @@ typedef unsigned long ptr_type; * A sort of pseudo-filename for data provided inline within * the configuration file. */ -#if ENABLE_INLINE_FILES #define INLINE_FILE_TAG "[[INLINE]]" -#endif /* * Script security warning diff --git a/openvpn/src/openvpn/crypto.c b/openvpn/src/openvpn/crypto.c index 03781fc4..ac2eecdd 100644 --- a/openvpn/src/openvpn/crypto.c +++ b/openvpn/src/openvpn/crypto.c @@ -737,7 +737,6 @@ get_tls_handshake_key (const struct key_type *key_type, kt.cipher_length = 0; kt.cipher = NULL; -#if ENABLE_INLINE_FILES if (flags & GHK_INLINE) { /* key was specified inline, key text is in passphrase_file */ @@ -750,7 +749,6 @@ get_tls_handshake_key (const struct key_type *key_type, msg (M_FATAL, "INLINE tls-auth file lacks the requisite 2 keys"); } else -#endif { /* first try to parse as an OpenVPN static key file */ read_key_file (&key2, passphrase_file, 0); @@ -857,7 +855,6 @@ read_key_file (struct key2 *key2, const char *file, const unsigned int flags) * Key can be provided as a filename in 'file' or if RKF_INLINE * is set, the actual key data itself in ascii form. */ -#if ENABLE_INLINE_FILES if (flags & RKF_INLINE) /* 'file' is a string containing ascii representation of key */ { size = strlen (file) + 1; @@ -865,7 +862,6 @@ read_key_file (struct key2 *key2, const char *file, const unsigned int flags) error_filename = INLINE_FILE_TAG; } else /* 'file' is a filename which refers to a file containing the ascii key */ -#endif { in = alloc_buf_gc (2048, &gc); fd = platform_open (file, O_RDONLY, 0); @@ -979,9 +975,7 @@ read_key_file (struct key2 *key2, const char *file, const unsigned int flags) } /* zero file read buffer if not an inline file */ -#if ENABLE_INLINE_FILES if (!(flags & RKF_INLINE)) -#endif buf_clear (&in); if (key2->n) diff --git a/openvpn/src/openvpn/error.c b/openvpn/src/openvpn/error.c index d6ad6393..8396fe01 100644 --- a/openvpn/src/openvpn/error.c +++ b/openvpn/src/openvpn/error.c @@ -221,10 +221,7 @@ void x_msg (const unsigned int flags, const char *format, ...) return; #endif - if (flags & M_ERRNO_SOCK) - e = openvpn_errno_socket (); - else - e = openvpn_errno (); + e = openvpn_errno (); /* * Apply muting filter. @@ -245,7 +242,7 @@ void x_msg (const unsigned int flags, const char *format, ...) va_end (arglist); m1[ERR_BUF_SIZE - 1] = 0; /* windows vsnprintf needs this */ - if ((flags & (M_ERRNO|M_ERRNO_SOCK)) && e) + if ((flags & M_ERRNO) && e) { openvpn_snprintf (m2, ERR_BUF_SIZE, "%s: %s (errno=%d)", m1, strerror_ts (e, &gc), e); @@ -596,7 +593,7 @@ x_check_status (int status, struct link_socket *sock, struct tuntap *tt) { - const int my_errno = (sock ? openvpn_errno_socket () : (int)openvpn_errno ()); + const int my_errno = openvpn_errno (); const char *extended_msg = NULL; msg (x_cs_verbose_level, "%s %s returned %d", diff --git a/openvpn/src/openvpn/error.h b/openvpn/src/openvpn/error.h index ed8f9036..aedb7c37 100644 --- a/openvpn/src/openvpn/error.h +++ b/openvpn/src/openvpn/error.h @@ -68,12 +68,10 @@ struct gc_arena; #ifdef WIN32 # define openvpn_errno() GetLastError() -# define openvpn_errno_socket() WSAGetLastError() # define openvpn_strerror(e, gc) strerror_win32(e, gc) const char *strerror_win32 (DWORD errnum, struct gc_arena *gc); #else # define openvpn_errno() errno -# define openvpn_errno_socket() errno # define openvpn_strerror(x, gc) strerror(x) #endif @@ -94,7 +92,6 @@ extern int x_msg_line_num; #define M_DEBUG (1<<7) #define M_ERRNO (1<<8) /* show errno description */ -#define M_ERRNO_SOCK (1<<9) /* show socket errno description */ #ifdef ENABLE_CRYPTO_OPENSSL # define M_SSL (1<<10) /* show SSL error */ @@ -110,7 +107,6 @@ extern int x_msg_line_num; /* flag combinations which are frequently used */ #define M_ERR (M_FATAL | M_ERRNO) -#define M_SOCKERR (M_FATAL | M_ERRNO_SOCK) #define M_SSLERR (M_FATAL | M_SSL) #define M_USAGE (M_USAGE_SMALL | M_NOPREFIX | M_OPTERR) #define M_CLIENT (M_MSG_VIRT_OUT | M_NOMUTE | M_NOIPREFIX) diff --git a/openvpn/src/openvpn/fdmisc.c b/openvpn/src/openvpn/fdmisc.c index 8dc11b1b..7fe449c5 100644 --- a/openvpn/src/openvpn/fdmisc.c +++ b/openvpn/src/openvpn/fdmisc.c @@ -66,7 +66,7 @@ void set_nonblock (int fd) { if (!set_nonblock_action (fd)) - msg (M_SOCKERR, "Set socket to non-blocking mode failed"); + msg (M_ERR, "Set socket to non-blocking mode failed"); } /* Set a file descriptor to not be passed across execs */ diff --git a/openvpn/src/openvpn/init.c b/openvpn/src/openvpn/init.c index a25de5d2..993a1f27 100644 --- a/openvpn/src/openvpn/init.c +++ b/openvpn/src/openvpn/init.c @@ -111,102 +111,99 @@ update_options_ce_post (struct options *options) #endif } -#if HTTP_PROXY_FALLBACK - +#ifdef ENABLE_MANAGEMENT static bool -ce_http_proxy_fallback_defined(const struct context *c) +management_callback_proxy_cmd (void *arg, const char **p) { - const struct connection_list *l = c->options.connection_list; - if (l && l->current == 0) - { - int i; - for (i = 0; i < l->len; ++i) - { - const struct connection_entry *ce = l->array[i]; - if (ce->flags & CE_HTTP_PROXY_FALLBACK) - return true; - } - } - return false; -} + struct context *c = arg; + struct connection_entry *ce = &c->options.ce; + struct gc_arena *gc = &c->c2.gc; + bool ret = false; -static void -ce_http_proxy_fallback_start(struct context *c, const char *remote_ip_hint) -{ - const struct connection_list *l = c->options.connection_list; - if (l) - { - int i; - for (i = 0; i < l->len; ++i) - { - struct connection_entry *ce = l->array[i]; - if (ce->flags & CE_HTTP_PROXY_FALLBACK) - { - ce->http_proxy_options = NULL; - ce->ce_http_proxy_fallback_timestamp = 0; - if (!remote_ip_hint) - remote_ip_hint = ce->remote; - } - } + update_time(); + if (streq (p[1], "NONE")) + ret = true; + else if (p[2] && p[3]) + { + const int port = atoi(p[3]); + if (!legal_ipv4_port (port)) + { + msg (M_WARN, "Bad proxy port number: %s", p[3]); + return false; + } + + if (streq (p[1], "HTTP")) + { +#ifndef ENABLE_HTTP_PROXY + msg (M_WARN, "HTTP proxy support is not available"); +#else + struct http_proxy_options *ho; + if (ce->proto != PROTO_TCPv4 && ce->proto != PROTO_TCPv4_CLIENT && + ce->proto != PROTO_TCPv6 && ce->proto != PROTO_TCPv6_CLIENT) + { + msg (M_WARN, "HTTP proxy support only works for TCP based connections"); + return false; + } + ho = init_http_proxy_options_once (ce->http_proxy_options, gc); + ho->server = string_alloc (p[2], gc); + ho->port = port; + ho->retry = true; + ho->auth_retry = (p[4] && streq (p[4], "nct") ? PAR_NCT : PAR_ALL); + ce->http_proxy_options = ho; + ret = true; +#endif + } + else if (streq (p[1], "SOCKS")) + { +#ifndef ENABLE_SOCKS + msg (M_WARN, "SOCKS proxy support is not available"); +#else + ce->socks_proxy_server = string_alloc (p[2], gc); + ce->socks_proxy_port = port; + ret = true; +#endif + } } + else + msg (M_WARN, "Bad proxy command"); - if (management) - management_http_proxy_fallback_notify(management, "NEED_LATER", remote_ip_hint); -} - -static bool -ce_http_proxy_fallback (struct context *c, volatile const struct connection_entry *ce) -{ - const int proxy_info_expire = 120; /* seconds before proxy info expires */ + ce->flags &= ~CE_MAN_QUERY_PROXY; - update_time(); - if (management) - { - if (!ce->ce_http_proxy_fallback_timestamp) - { - management_http_proxy_fallback_notify(management, "NEED_NOW", NULL); - while (!ce->ce_http_proxy_fallback_timestamp) - { - management_event_loop_n_seconds (management, 1); - if (IS_SIG (c)) - return false; - } - } - return (now < ce->ce_http_proxy_fallback_timestamp + proxy_info_expire && ce->http_proxy_options); - } - return false; + return ret; } static bool -management_callback_http_proxy_fallback_cmd (void *arg, const char *server, const char *port, const char *flags) +ce_management_query_proxy (struct context *c) { - struct context *c = (struct context *) arg; const struct connection_list *l = c->options.connection_list; - int ret = false; - struct http_proxy_options *ho = parse_http_proxy_fallback (c, server, port, flags, M_WARN); + struct connection_entry *ce = &c->options.ce; + struct gc_arena gc; + bool ret = true; update_time(); - if (l) + if (management) { - int i; - for (i = 0; i < l->len; ++i) - { - struct connection_entry *ce = l->array[i]; - if (ce->flags & CE_HTTP_PROXY_FALLBACK) - { - ce->http_proxy_options = ho; - ce->ce_http_proxy_fallback_timestamp = now; - ret = true; - } - } + gc = gc_new (); + struct buffer out = alloc_buf_gc (256, &gc); + buf_printf (&out, ">PROXY:%u,%s,%s", (l ? l->current : 0) + 1, + (proto_is_udp (ce->proto) ? "UDP" : "TCP"), np (ce->remote)); + management_notify_generic (management, BSTR (&out)); + ce->flags |= CE_MAN_QUERY_PROXY; + while (ce->flags & CE_MAN_QUERY_PROXY) + { + management_event_loop_n_seconds (management, 1); + if (IS_SIG (c)) + { + ret = false; + break; + } + } + gc_free (&gc); } - + return ret; } -#endif - -#if MANAGEMENT_QUERY_REMOTE static bool management_callback_remote_cmd (void *arg, const char **p) @@ -287,8 +284,7 @@ ce_management_query_remote (struct context *c, const char *remote_ip_hint) gc_free (&gc); return ret; } - -#endif +#endif /* ENABLE_MANAGEMENT */ /* * Initialize and possibly randomize connection list. @@ -296,7 +292,6 @@ ce_management_query_remote (struct context *c, const char *remote_ip_hint) static void init_connection_list (struct context *c) { -#ifdef ENABLE_CONNECTION struct connection_list *l = c->options.connection_list; if (l) { @@ -317,32 +312,7 @@ init_connection_list (struct context *c) } } } -#endif -} - -#if 0 /* fixme -- disable for production */ -static void -show_connection_list (const struct connection_list *l) -{ - int i; - dmsg (M_INFO, "CONNECTION_LIST len=%d current=%d", - l->len, l->current); - for (i = 0; i < l->len; ++i) - { - dmsg (M_INFO, "[%d] %s:%d proto=%s http_proxy=%d", - i, - l->array[i]->remote, - l->array[i]->remote_port, - proto2ascii(l->array[i]->proto, true), - BOOL_CAST(l->array[i]->http_proxy_options)); - } -} -#else -static inline void -show_connection_list (const struct connection_list *l) -{ } -#endif /* * Increment to next connection entry @@ -350,7 +320,6 @@ show_connection_list (const struct connection_list *l) static void next_connection_entry (struct context *c) { -#ifdef ENABLE_CONNECTION struct connection_list *l = c->options.connection_list; if (l) { @@ -379,7 +348,6 @@ next_connection_entry (struct context *c) if (l->current == 0) newcycle = true; - show_connection_list(l); } ce = l->array[l->current]; @@ -387,44 +355,33 @@ next_connection_entry (struct context *c) if (c->options.remote_ip_hint && !l->n_cycles) remote_ip_hint = c->options.remote_ip_hint; -#if HTTP_PROXY_FALLBACK - if (newcycle && ce_http_proxy_fallback_defined(c)) - ce_http_proxy_fallback_start(c, remote_ip_hint); - - if (ce->flags & CE_HTTP_PROXY_FALLBACK) - { - ce_defined = ce_http_proxy_fallback(c, ce); - if (IS_SIG (c)) - break; - } -#endif - if (ce->flags & CE_DISABLED) ce_defined = false; c->options.ce = *ce; - -#if MANAGEMENT_QUERY_REMOTE +#ifdef ENABLE_MANAGEMENT if (ce_defined && management && management_query_remote_enabled(management)) { /* allow management interface to override connection entry details */ ce_defined = ce_management_query_remote(c, remote_ip_hint); if (IS_SIG (c)) break; - } else + } + else #endif if (remote_ip_hint) c->options.ce.remote = remote_ip_hint; -#if 0 /* fixme -- disable for production, this code simulates a network where proxy fallback is the only method to reach the OpenVPN server */ - if (!(c->options.ce.flags & CE_HTTP_PROXY_FALLBACK)) - { - c->options.ce.remote = "10.10.0.1"; /* use an unreachable address here */ - } +#ifdef ENABLE_MANAGEMENT + if (ce_defined && management && management_query_proxy_enabled (management)) + { + ce_defined = ce_management_query_proxy (c); + if (IS_SIG (c)) + break; + } #endif } while (!ce_defined); } -#endif update_options_ce_post (&c->options); } @@ -498,11 +455,10 @@ init_proxy_dowork (struct context *c) uninit_proxy_dowork (c); #ifdef ENABLE_HTTP_PROXY - if (c->options.ce.http_proxy_options || c->options.auto_proxy_info) + if (c->options.ce.http_proxy_options) { /* Possible HTTP proxy user/pass input */ - c->c1.http_proxy = http_proxy_new (c->options.ce.http_proxy_options, - c->options.auto_proxy_info); + c->c1.http_proxy = http_proxy_new (c->options.ce.http_proxy_options); if (c->c1.http_proxy) { did_http = true; @@ -512,13 +468,12 @@ init_proxy_dowork (struct context *c) #endif #ifdef ENABLE_SOCKS - if (!did_http && (c->options.ce.socks_proxy_server || c->options.auto_proxy_info)) + if (!did_http && c->options.ce.socks_proxy_server) { c->c1.socks_proxy = socks_proxy_new (c->options.ce.socks_proxy_server, c->options.ce.socks_proxy_port, c->options.ce.socks_proxy_authfile, - c->options.ce.socks_proxy_retry, - c->options.auto_proxy_info); + c->options.ce.socks_proxy_retry); if (c->c1.socks_proxy) { c->c1.socks_proxy_owned = true; @@ -1251,10 +1206,7 @@ do_init_route_ipv6_list (const struct options *options, { const char *gw = NULL; int dev = dev_type_enum (options->dev, options->dev_type); - int metric = 0; - - if (dev != DEV_TYPE_TUN ) - msg( M_WARN, "IPv6 routes on TAP devices are going to fail on some platforms (need gateway spec)" ); /* TODO-GERT */ + int metric = -1; /* no metric set */ gw = options->ifconfig_ipv6_remote; /* default GW = remote end */ #if 0 /* not yet done for IPv6 - TODO!*/ @@ -2065,13 +2017,11 @@ do_init_crypto_static (struct context *c, const unsigned int flags) unsigned int rkf_flags = RKF_MUST_SUCCEED; const char *rkf_file = options->shared_secret_file; -#if ENABLE_INLINE_FILES if (options->shared_secret_file_inline) { rkf_file = options->shared_secret_file_inline; rkf_flags |= RKF_INLINE; } -#endif read_key_file (&key2, rkf_file, rkf_flags); } @@ -2165,13 +2115,11 @@ do_init_crypto_tls_c1 (struct context *c) unsigned int flags = 0; const char *file = options->tls_auth_file; -#if ENABLE_INLINE_FILES if (options->tls_auth_file_inline) { flags |= GHK_INLINE; file = options->tls_auth_file_inline; } -#endif get_tls_handshake_key (&c->c1.ks.key_type, &c->c1.ks.tls_auth_key, file, @@ -2474,12 +2422,6 @@ do_option_warnings (struct context *c) { const struct options *o = &c->options; -#if 1 /* JYFIXME -- port warning */ - if (!o->ce.port_option_used && (o->ce.local_port == OPENVPN_PORT && o->ce.remote_port == OPENVPN_PORT)) - msg (M_WARN, "IMPORTANT: OpenVPN's default port number is now %d, based on an official port number assignment by IANA. OpenVPN 2.0-beta16 and earlier used 5000 as the default port.", - OPENVPN_PORT); -#endif - if (o->ping_send_timeout && !o->ping_rec_timeout) msg (M_WARN, "WARNING: --ping should normally be used with --ping-restart or --ping-exit"); @@ -3197,12 +3139,8 @@ init_management_callback_p2p (struct context *c) cb.arg = c; cb.status = management_callback_status_p2p; cb.show_net = management_show_net_callback; -#if HTTP_PROXY_FALLBACK - cb.http_proxy_fallback_cmd = management_callback_http_proxy_fallback_cmd; -#endif -#if MANAGEMENT_QUERY_REMOTE + cb.proxy_cmd = management_callback_proxy_cmd; cb.remote_cmd = management_callback_remote_cmd; -#endif management_set_callback (management, &cb); } #endif diff --git a/openvpn/src/openvpn/manage.c b/openvpn/src/openvpn/manage.c index cc22208e..77d40833 100644 --- a/openvpn/src/openvpn/manage.c +++ b/openvpn/src/openvpn/manage.c @@ -92,9 +92,8 @@ man_help () msg (M_CLIENT, " where action is reply string."); msg (M_CLIENT, "net : (Windows only) Show network info and routing table."); msg (M_CLIENT, "password type p : Enter password p for a queried OpenVPN password."); -#if MANAGEMENT_QUERY_REMOTE msg (M_CLIENT, "remote type [host port] : Override remote directive, type=ACCEPT|MOD|SKIP."); -#endif + msg (M_CLIENT, "proxy type [host port flags] : Enter dynamic proxy server info."); msg (M_CLIENT, "pid : Show process ID of the current OpenVPN process."); #ifdef ENABLE_PKCS11 msg (M_CLIENT, "pkcs11-id-count : Get number of available PKCS#11 identities."); @@ -123,10 +122,6 @@ man_help () msg (M_CLIENT, "username type u : Enter username u for a queried OpenVPN username."); msg (M_CLIENT, "verb [n] : Set log verbosity level to n, or show if n is absent."); msg (M_CLIENT, "version : Show current version number."); -#if HTTP_PROXY_FALLBACK - msg (M_CLIENT, "http-proxy-fallback [flags] : Enter dynamic HTTP proxy fallback info."); - msg (M_CLIENT, "http-proxy-fallback-disable : Disable HTTP proxy fallback."); -#endif msg (M_CLIENT, "END"); } @@ -1073,33 +1068,21 @@ man_need (struct management *man, const char **p, const int n, unsigned int flag return true; } -#if HTTP_PROXY_FALLBACK - static void -man_http_proxy_fallback (struct management *man, const char *server, const char *port, const char *flags) +man_proxy (struct management *man, const char **p) { - if (man->persist.callback.http_proxy_fallback_cmd) + if (man->persist.callback.proxy_cmd) { - const bool status = (*man->persist.callback.http_proxy_fallback_cmd)(man->persist.callback.arg, server, port, flags); + const bool status = (*man->persist.callback.proxy_cmd)(man->persist.callback.arg, p); if (status) - { - msg (M_CLIENT, "SUCCESS: proxy-fallback command succeeded"); - } + msg (M_CLIENT, "SUCCESS: proxy command succeeded"); else - { - msg (M_CLIENT, "ERROR: proxy-fallback command failed"); - } + msg (M_CLIENT, "ERROR: proxy command failed"); } else - { - msg (M_CLIENT, "ERROR: The proxy-fallback command is not supported by the current daemon mode"); - } + msg (M_CLIENT, "ERROR: The proxy command is not supported by the current daemon mode"); } -#endif - -#if MANAGEMENT_QUERY_REMOTE - static void man_remote (struct management *man, const char **p) { @@ -1121,8 +1104,6 @@ man_remote (struct management *man, const char **p) } } -#endif - static void man_dispatch_command (struct management *man, struct status_output *so, const char **p, const int nparms) { @@ -1341,24 +1322,16 @@ man_dispatch_command (struct management *man, struct status_output *so, const ch man_pkcs11_id_get (man, atoi(p[1])); } #endif -#if HTTP_PROXY_FALLBACK - else if (streq (p[0], "http-proxy-fallback")) - { - if (man_need (man, p, 2, MN_AT_LEAST)) - man_http_proxy_fallback (man, p[1], p[2], p[3]); - } - else if (streq (p[0], "http-proxy-fallback-disable")) + else if (streq (p[0], "proxy")) { - man_http_proxy_fallback (man, NULL, NULL, NULL); + if (man_need (man, p, 1, MN_AT_LEAST)) + man_proxy (man, p); } -#endif -#if MANAGEMENT_QUERY_REMOTE else if (streq (p[0], "remote")) { if (man_need (man, p, 1, MN_AT_LEAST)) man_remote (man, p); } -#endif #if 1 else if (streq (p[0], "test")) { @@ -1602,7 +1575,7 @@ man_listen (struct management *man) * Listen for connection */ if (listen (man->connection.sd_top, 1)) - msg (M_SOCKERR, "MANAGEMENT: listen() failed"); + msg (M_ERR, "MANAGEMENT: listen() failed"); /* * Set misc socket properties @@ -1790,7 +1763,7 @@ man_process_command (struct management *man, const char *line) static bool man_io_error (struct management *man, const char *prefix) { - const int err = openvpn_errno_socket (); + const int err = openvpn_errno (); if (!ignore_sys_error (err)) { @@ -3441,19 +3414,6 @@ log_history_ref (const struct log_history *h, const int index) return NULL; } -#if HTTP_PROXY_FALLBACK - -void -management_http_proxy_fallback_notify (struct management *man, const char *type, const char *remote_ip_hint) -{ - if (remote_ip_hint) - msg (M_CLIENT, ">PROXY:%s,%s", type, remote_ip_hint); - else - msg (M_CLIENT, ">PROXY:%s", type); -} - -#endif /* HTTP_PROXY_FALLBACK */ - #else static void dummy(void) {} #endif /* ENABLE_MANAGEMENT */ diff --git a/openvpn/src/openvpn/manage.h b/openvpn/src/openvpn/manage.h index 991b4896..eec24a2e 100644 --- a/openvpn/src/openvpn/manage.h +++ b/openvpn/src/openvpn/manage.h @@ -171,12 +171,8 @@ struct management_callback const unsigned long cid, struct buffer_list *pf_config); /* ownership transferred */ #endif -#if HTTP_PROXY_FALLBACK - bool (*http_proxy_fallback_cmd) (void *arg, const char *server, const char *port, const char *flags); -#endif -#if MANAGEMENT_QUERY_REMOTE + bool (*proxy_cmd) (void *arg, const char **p); bool (*remote_cmd) (void *arg, const char **p); -#endif }; /* @@ -340,9 +336,8 @@ struct management *management_init (void); # define MF_EXTERNAL_KEY (1<<9) #endif #define MF_UP_DOWN (1<<10) -#if MANAGEMENT_QUERY_REMOTE #define MF_QUERY_REMOTE (1<<11) -#endif +#define MF_QUERY_PROXY (1<<12) bool management_open (struct management *man, const char *addr, @@ -431,13 +426,17 @@ management_query_user_pass_enabled (const struct management *man) return BOOL_CAST(man->settings.flags & MF_QUERY_PASSWORDS); } -#if MANAGEMENT_QUERY_REMOTE static inline bool management_query_remote_enabled (const struct management *man) { return BOOL_CAST(man->settings.flags & MF_QUERY_REMOTE); } -#endif + +static inline bool +management_query_proxy_enabled (const struct management *man) +{ + return BOOL_CAST(man->settings.flags & MF_QUERY_PROXY); +} #ifdef MANAGEMENT_PF static inline bool @@ -564,11 +563,5 @@ management_bytes_server (struct management *man, #endif /* MANAGEMENT_DEF_AUTH */ -#if HTTP_PROXY_FALLBACK - -void management_http_proxy_fallback_notify (struct management *man, const char *type, const char *remote_ip_hint); - -#endif /* HTTP_PROXY_FALLBACK */ - #endif #endif diff --git a/openvpn/src/openvpn/misc.c b/openvpn/src/openvpn/misc.c index 2ded9bfc..7f729390 100644 --- a/openvpn/src/openvpn/misc.c +++ b/openvpn/src/openvpn/misc.c @@ -205,9 +205,7 @@ warn_if_group_others_accessible (const char* filename) { #ifndef WIN32 #ifdef HAVE_STAT -#if ENABLE_INLINE_FILES if (strcmp (filename, INLINE_FILE_TAG)) -#endif { struct stat st; if (stat (filename, &st)) @@ -1524,7 +1522,6 @@ make_arg_array (const char *first, const char *parms, struct gc_arena *gc) return (const char **)ret; } -#if ENABLE_INLINE_FILES static const char ** make_inline_array (const char *str, struct gc_arena *gc) { @@ -1553,7 +1550,6 @@ make_inline_array (const char *str, struct gc_arena *gc) ret[i] = NULL; return (const char **)ret; } -#endif static const char ** make_arg_copy (char **p, struct gc_arena *gc) @@ -1576,11 +1572,9 @@ const char ** make_extended_arg_array (char **p, struct gc_arena *gc) { const int argc = string_array_len ((const char **)p); -#if ENABLE_INLINE_FILES if (!strcmp (p[0], INLINE_FILE_TAG) && argc == 2) return make_inline_array (p[1], gc); else -#endif if (argc == 0) return make_arg_array (NULL, NULL, gc); else if (argc == 1) diff --git a/openvpn/src/openvpn/mroute.c b/openvpn/src/openvpn/mroute.c index aecb7027..850e3363 100644 --- a/openvpn/src/openvpn/mroute.c +++ b/openvpn/src/openvpn/mroute.c @@ -52,7 +52,7 @@ mroute_addr_init (struct mroute_addr *addr) static inline bool is_mac_mcast_addr (const uint8_t *mac) { - return (bool) mac[0] & 1; + return (bool) (mac[0] & 1); } static inline bool diff --git a/openvpn/src/openvpn/openvpn.c b/openvpn/src/openvpn/openvpn.c index 75c751d5..104c9e93 100644 --- a/openvpn/src/openvpn/openvpn.c +++ b/openvpn/src/openvpn/openvpn.c @@ -127,8 +127,9 @@ tunnel_point_to_point (struct context *c) * @param argc - Commandline argument count. * @param argv - Commandline argument values. */ +static int -main (int argc, char *argv[]) +openvpn_main (int argc, char *argv[]) { struct context c; @@ -289,3 +290,37 @@ main (int argc, char *argv[]) openvpn_exit (OPENVPN_EXIT_STATUS_GOOD); /* exit point */ return 0; /* NOTREACHED */ } + +#ifdef WIN32 +int +wmain (int argc, wchar_t *wargv[]) { + char **argv; + int ret; + int i; + + if ((argv = calloc(argc+1, sizeof(char*))) == NULL) + return 1; + + for (i = 0; i < argc; i++) + { + int n = WideCharToMultiByte (CP_UTF8, 0, wargv[i], -1, NULL, 0, NULL, NULL); + argv[i] = malloc (n); + WideCharToMultiByte (CP_UTF8, 0, wargv[i], -1, argv[i], n, NULL, NULL); + } + + ret = openvpn_main(argc, argv); + + for (i=0; i < argc; i++ ) + { + free (argv[i]); + } + free(argv); + + return ret; +} +#else +int +main (int argc, char *argv[]) { + return openvpn_main(argc, argv); +} +#endif diff --git a/openvpn/src/openvpn/openvpn.vcxproj b/openvpn/src/openvpn/openvpn.vcxproj old mode 100644 new mode 100755 index 51e19aff..452876fc --- a/openvpn/src/openvpn/openvpn.vcxproj +++ b/openvpn/src/openvpn/openvpn.vcxproj @@ -18,12 +18,12 @@ Application - MultiByte true + Unicode Application - MultiByte + Unicode @@ -56,12 +56,13 @@ Level3 EditAndContinue + UNICODE $(SOURCEBASE);%(AdditionalIncludeDirectories) - libeay32.lib;ssleay32.lib;lzo2.lib;pkcs11-helper.dll.lib;gdi32.lib;ws2_32.lib;wininet.lib;crypt32.lib;iphlpapi.lib;winmm.lib;shell32.lib;%(AdditionalDependencies) + libeay32.lib;ssleay32.lib;lzo2.lib;pkcs11-helper.dll.lib;gdi32.lib;ws2_32.lib;wininet.lib;crypt32.lib;iphlpapi.lib;winmm.lib;%(AdditionalDependencies) $(OPENSSL_HOME)/lib;$(LZO_HOME)/lib;$(PKCS11H_HOME)/lib;%(AdditionalLibraryDirectories) true Console @@ -80,12 +81,13 @@ Level3 ProgramDatabase + UNICODE $(SOURCEBASE);%(AdditionalIncludeDirectories) - libeay32.lib;ssleay32.lib;lzo2.lib;pkcs11-helper.dll.lib;gdi32.lib;ws2_32.lib;wininet.lib;crypt32.lib;iphlpapi.lib;winmm.lib;shell32.lib;%(AdditionalDependencies) + libeay32.lib;ssleay32.lib;lzo2.lib;pkcs11-helper.dll.lib;gdi32.lib;ws2_32.lib;wininet.lib;crypt32.lib;iphlpapi.lib;winmm.lib;%(AdditionalDependencies) $(OPENSSL_HOME)/lib;$(LZO_HOME)/lib;$(PKCS11H_HOME)/lib;%(AdditionalLibraryDirectories) true Console diff --git a/openvpn/src/openvpn/options.c b/openvpn/src/openvpn/options.c index b3a41d7b..44b38bed 100644 --- a/openvpn/src/openvpn/options.c +++ b/openvpn/src/openvpn/options.c @@ -135,10 +135,6 @@ static const char usage_message[] = " between connection retries (default=%d).\n" "--connect-timeout n : For --proto tcp-client, connection timeout (in seconds).\n" "--connect-retry-max n : Maximum connection attempt retries, default infinite.\n" -#ifdef GENERAL_PROXY_SUPPORT - "--auto-proxy : Try to sense proxy settings (or lack thereof) automatically.\n" - "--show-proxy-settings : Show sensed proxy settings.\n" -#endif #ifdef ENABLE_HTTP_PROXY "--http-proxy s p [up] [auth] : Connect to remote host\n" " through an HTTP proxy at address s and port p.\n" @@ -385,9 +381,8 @@ static const char usage_message[] = " ip/port rather than listen as a TCP server.\n" "--management-query-passwords : Query management channel for private key\n" " and auth-user-pass passwords.\n" -#if MANAGEMENT_QUERY_REMOTE + "--management-query-proxy : Query management channel for proxy information.\n" "--management-query-remote : Query management channel for --remote directive.\n" -#endif "--management-hold : Start " PACKAGE_NAME " in a hibernating state, until a client\n" " of the management interface explicitly starts it.\n" "--management-signal : Issue SIGUSR1 when management disconnect event occurs.\n" @@ -862,7 +857,8 @@ init_options (struct options *o, const bool init_gc) o->pkcs11_pin_cache_period = -1; #endif /* ENABLE_PKCS11 */ -#ifdef ENABLE_TMPDIR +/* tmp is only used in P2MP server context */ +#if P2MP_SERVER /* Set default --tmp-dir */ #ifdef WIN32 /* On Windows, find temp dir via enviroment variables */ @@ -874,7 +870,7 @@ init_options (struct options *o, const bool init_gc) o->tmp_dir = "/tmp"; } #endif /* WIN32 */ -#endif /* ENABLE_TMPDIR */ +#endif /* P2MP_SERVER */ } void @@ -934,7 +930,6 @@ setenv_settings (struct env_set *es, const struct options *o) setenv_unsigned (es, "daemon_start_time", time(NULL)); setenv_int (es, "daemon_pid", platform_getpid()); -#ifdef ENABLE_CONNECTION if (o->connection_list) { int i; @@ -942,7 +937,6 @@ setenv_settings (struct env_set *es, const struct options *o) setenv_connection_entry (es, o->connection_list->array[i], i+1); } else -#endif setenv_connection_entry (es, &o->ce, 1); } @@ -1391,7 +1385,6 @@ show_connection_entries (const struct options *o) { msg (D_SHOW_PARMS, "Connection profiles [default]:"); show_connection_entry (&o->ce); -#ifdef ENABLE_CONNECTION if (o->connection_list) { const struct connection_list *l = o->connection_list; @@ -1402,7 +1395,6 @@ show_connection_entries (const struct options *o) show_connection_entry (l->array[i]); } } -#endif msg (D_SHOW_PARMS, "Connection profiles END"); } @@ -1674,24 +1666,7 @@ show_settings (const struct options *o) #undef SHOW_INT #undef SHOW_BOOL -#ifdef ENABLE_HTTP_PROXY - -struct http_proxy_options * -init_http_options_if_undefined (struct options *o) -{ - if (!o->ce.http_proxy_options) - { - ALLOC_OBJ_CLEAR_GC (o->ce.http_proxy_options, struct http_proxy_options, &o->gc); - /* http proxy defaults */ - o->ce.http_proxy_options->timeout = 5; - o->ce.http_proxy_options->http_version = "1.0"; - } - return o->ce.http_proxy_options; -} - -#endif - -#if HTTP_PROXY_FALLBACK +#if HTTP_PROXY_OVERRIDE static struct http_proxy_options * parse_http_proxy_override (const char *server, @@ -1728,68 +1703,6 @@ parse_http_proxy_override (const char *server, return NULL; } -struct http_proxy_options * -parse_http_proxy_fallback (struct context *c, - const char *server, - const char *port, - const char *flags, - const int msglevel) -{ - struct gc_arena gc = gc_new (); - struct http_proxy_options *ret = NULL; - struct http_proxy_options *hp = parse_http_proxy_override(server, port, flags, msglevel, &gc); - if (hp) - { - struct hpo_store *hpos = c->options.hpo_store; - if (!hpos) - { - ALLOC_OBJ_CLEAR_GC (hpos, struct hpo_store, &c->options.gc); - c->options.hpo_store = hpos; - } - hpos->hpo = *hp; - hpos->hpo.server = hpos->server; - strncpynt(hpos->server, hp->server, sizeof(hpos->server)); - ret = &hpos->hpo; - } - gc_free (&gc); - return ret; -} - -static void -http_proxy_warn(const char *name) -{ - msg (M_WARN, "Note: option %s ignored because no TCP-based connection profiles are defined", name); -} - -void -options_postprocess_http_proxy_fallback (struct options *o) -{ - struct connection_list *l = o->connection_list; - if (l) - { - int i; - for (i = 0; i < l->len; ++i) - { - struct connection_entry *ce = l->array[i]; - if (ce->proto == PROTO_TCPv4_CLIENT || ce->proto == PROTO_TCPv4) - { - if (l->len < CONNECTION_LIST_SIZE) - { - struct connection_entry *newce; - ALLOC_OBJ_GC (newce, struct connection_entry, &o->gc); - *newce = *ce; - newce->flags |= CE_HTTP_PROXY_FALLBACK; - newce->http_proxy_options = NULL; - newce->ce_http_proxy_fallback_timestamp = 0; - l->array[l->len++] = newce; - } - return; - } - } - } - http_proxy_warn("http-proxy-fallback"); -} - void options_postprocess_http_proxy_override (struct options *o) { @@ -1819,16 +1732,12 @@ options_postprocess_http_proxy_override (struct options *o) } } else - { - http_proxy_warn("http-proxy-override"); - } + msg (M_WARN, "Note: option http-proxy-override ignored because no TCP-based connection profiles are defined"); } } #endif -#if ENABLE_CONNECTION - static struct connection_list * alloc_connection_list_if_undef (struct options *options) { @@ -1877,8 +1786,6 @@ alloc_remote_entry (struct options *options, const int msglevel) return e; } -#endif - void connection_entry_load_re (struct connection_entry *ce, const struct remote_entry *re) { @@ -2025,6 +1932,15 @@ options_postprocess_verify_ce (const struct options *options, const struct conne if ((options->management_client_user || options->management_client_group) && !(options->management_flags & MF_UNIX_SOCK)) msg (M_USAGE, "--management-client-(user|group) can only be used on unix domain sockets"); +#ifdef MANAGMENT_EXTERNAL_KEY + if(options->management_flags & MF_EXTERNAL_KEY) { + if(options->priv_key_file) + msg (M_USAGE, "--key and --management-external-key are mutually exclusive"); + /* set a filename for nicer output in the logs */ + options->priv_key_file = "EXTERNAL_PRIVATE_KEY"; + } +#endif + #endif /* @@ -2064,8 +1980,8 @@ options_postprocess_verify_ce (const struct options *options, const struct conne msg (M_USAGE, "--remote MUST be used in TCP Client mode"); #ifdef ENABLE_HTTP_PROXY - if ((ce->http_proxy_options || options->auto_proxy_info) && ce->proto != PROTO_TCPv4_CLIENT) - msg (M_USAGE, "--http-proxy or --auto-proxy MUST be used in TCP Client mode (i.e. --proto tcp-client)"); + if ((ce->http_proxy_options) && ce->proto != PROTO_TCPv4_CLIENT) + msg (M_USAGE, "--http-proxy MUST be used in TCP Client mode (i.e. --proto tcp-client)"); #endif #if defined(ENABLE_HTTP_PROXY) && defined(ENABLE_SOCKS) @@ -2117,10 +2033,8 @@ options_postprocess_verify_ce (const struct options *options, const struct conne if (ce->socks_proxy_server) msg (M_USAGE, "--socks-proxy cannot be used with --mode server"); #endif -#ifdef ENABLE_CONNECTION if (options->connection_list) msg (M_USAGE, " cannot be used with --mode server"); -#endif #if 0 if (options->tun_ipv6) msg (M_USAGE, "--tun-ipv6 cannot be used with --mode server"); @@ -2521,7 +2435,6 @@ options_postprocess_mutate_invariant (struct options *options) static void options_postprocess_verify (const struct options *o) { -#ifdef ENABLE_CONNECTION if (o->connection_list) { int i; @@ -2529,7 +2442,6 @@ options_postprocess_verify (const struct options *o) options_postprocess_verify_ce (o, o->connection_list->array[i]); } else -#endif options_postprocess_verify_ce (o, &o->ce); } @@ -2546,7 +2458,6 @@ options_postprocess_mutate (struct options *o) options_postprocess_mutate_invariant (o); -#ifdef ENABLE_CONNECTION if (o->remote_list && !o->connection_list) { /* @@ -2585,15 +2496,12 @@ options_postprocess_mutate (struct options *o) for (i = 0; i < o->connection_list->len; ++i) options_postprocess_mutate_ce (o, o->connection_list->array[i]); -#if HTTP_PROXY_FALLBACK +#if HTTP_PROXY_OVERRIDE if (o->http_proxy_override) options_postprocess_http_proxy_override(o); - else if (o->http_proxy_fallback) - options_postprocess_http_proxy_fallback(o); #endif } else -#endif options_postprocess_mutate_ce (o, &o->ce); #if P2MP @@ -2730,9 +2638,8 @@ options_postprocess_filechecks (struct options *options) errs |= check_file_access (CHKACC_FILE|CHKACC_INLINE, options->cert_file, R_OK, "--cert"); errs |= check_file_access (CHKACC_FILE|CHKACC_INLINE, options->extra_certs_file, R_OK, "--extra-certs"); - #ifdef MANAGMENT_EXTERNAL_KEY - if(!(options->management_flags & MF_EXTERNAL_KEY)) + if(!options->management_flags & MF_EXTERNAL_KEY) #endif errs |= check_file_access (CHKACC_FILE|CHKACC_INLINE, options->priv_key_file, R_OK, "--key"); @@ -2767,15 +2674,11 @@ options_postprocess_filechecks (struct options *options) options->management_user_pass, R_OK, "--management user/password file"); #endif /* ENABLE_MANAGEMENT */ -#if ENABLE_TMPDIR +#if P2MP errs |= check_file_access (CHKACC_FILE|CHKACC_ACPTSTDIN, options->auth_user_pass_file, R_OK, "--auth-user-pass"); - - errs |= check_file_access (CHKACC_FILE, options->tmp_dir, - R_OK|W_OK|X_OK, "Temporary directory (--tmp-dir)"); - -#endif /* ENABLE_TMPDIR */ +#endif /* P2MP */ /* ** System related ** */ errs |= check_file_access (CHKACC_FILE, options->chroot_dir, @@ -2795,6 +2698,8 @@ options_postprocess_filechecks (struct options *options) #if P2MP_SERVER errs |= check_file_access (CHKACC_FILE, options->client_config_dir, R_OK|X_OK, "--client-config-dir"); + errs |= check_file_access (CHKACC_FILE, options->tmp_dir, + R_OK|W_OK|X_OK, "Temporary directory (--tmp-dir)"); /* ** Script hooks that accept an optionally quoted and/or escaped executable path, ** */ /* ** optionally followed by arguments ** */ @@ -3478,6 +3383,9 @@ usage_version (void) #ifdef CONFIGURE_DEFINES msg (M_INFO|M_NOPREFIX, "Compile time defines: %s", CONFIGURE_DEFINES); #endif +#ifdef CONFIGURE_SPECIAL_BUILD + msg (M_INFO|M_NOPREFIX, "special build: %s", CONFIGURE_SPECIAL_BUILD); +#endif #ifdef CONFIGURE_GIT_REVISION msg (M_INFO|M_NOPREFIX, "git revision: %s", CONFIGURE_GIT_REVISION); #endif @@ -3691,8 +3599,6 @@ bypass_doubledash (char **p) *p += 2; } -#if ENABLE_INLINE_FILES - struct in_src { # define IS_TYPE_FP 1 # define IS_TYPE_BUF 2 @@ -3785,8 +3691,6 @@ check_inline_file_via_buf (struct buffer *multiline, char *p[], struct gc_arena return check_inline_file (&is, p, gc); } -#endif - static void add_option (struct options *options, char *p[], @@ -3832,9 +3736,7 @@ read_config_file (struct options *options, if (parse_line (line, p, SIZE (p), file, line_num, msglevel, &options->gc)) { bypass_doubledash (&p[0]); -#if ENABLE_INLINE_FILES check_inline_file_via_fp (fp, p, &options->gc); -#endif add_option (options, p, file, line_num, level, msglevel, permission_mask, option_types_found, es); } } @@ -3877,9 +3779,7 @@ read_config_string (const char *prefix, if (parse_line (line, p, SIZE (p), prefix, line_num, msglevel, &options->gc)) { bypass_doubledash (&p[0]); -#if ENABLE_INLINE_FILES check_inline_file_via_buf (&multiline, p, &options->gc); -#endif add_option (options, p, NULL, line_num, 0, msglevel, permission_mask, option_types_found, es); } CLEAR (p); @@ -3898,33 +3798,6 @@ parse_argv (struct options *options, { int i, j; -#ifdef WIN32 - /* - * Windows replaces Unicode characters in argv[] that are not present - * in the current codepage with '?'. Get the wide char command line and - * convert it to UTF-8 ourselves. - */ - int wargc; - WCHAR **wargv; - char **uargv; - - wargv = CommandLineToArgvW (GetCommandLineW (), &wargc); - if (wargv == NULL || wargc != argc) - usage (); - - uargv = gc_malloc (wargc * sizeof (*uargv), false, &options->gc); - - for (i = 0; i < wargc; i++) - { - int n = WideCharToMultiByte (CP_UTF8, 0, wargv[i], -1, NULL, 0, NULL, NULL); - uargv[i] = gc_malloc (n, false, &options->gc); - WideCharToMultiByte (CP_UTF8, 0, wargv[i], -1, uargv[i], n, NULL, NULL); - } - - LocalFree (wargv); - argv = uargv; -#endif - /* usage message */ if (argc <= 1) usage (); @@ -4240,13 +4113,17 @@ add_option (struct options *options, VERIFY_PERMISSION (OPT_P_GENERAL); options->management_flags |= MF_QUERY_PASSWORDS; } -#if MANAGEMENT_QUERY_REMOTE else if (streq (p[0], "management-query-remote")) { VERIFY_PERMISSION (OPT_P_GENERAL); options->management_flags |= MF_QUERY_REMOTE; } -#endif + else if (streq (p[0], "management-query-proxy")) + { + VERIFY_PERMISSION (OPT_P_GENERAL); + options->management_flags |= MF_QUERY_PROXY; + options->force_connection_list = true; + } else if (streq (p[0], "management-hold")) { VERIFY_PERMISSION (OPT_P_GENERAL); @@ -4278,7 +4155,6 @@ add_option (struct options *options, { VERIFY_PERMISSION (OPT_P_GENERAL); options->management_flags |= MF_EXTERNAL_KEY; - options->priv_key_file = "EXTERNAL_PRIVATE_KEY"; } #endif #ifdef MANAGEMENT_DEF_AUTH @@ -4450,7 +4326,6 @@ add_option (struct options *options, VERIFY_PERMISSION (OPT_P_GENERAL); options->remote_random = true; } -#if ENABLE_CONNECTION else if (streq (p[0], "connection") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); @@ -4476,21 +4351,12 @@ add_option (struct options *options, uninit_options (&sub); } } -#endif -#ifdef ENABLE_CONNECTION else if (streq (p[0], "remote-ip-hint") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); options->remote_ip_hint = p[1]; } -#endif -#if HTTP_PROXY_FALLBACK - else if (streq (p[0], "http-proxy-fallback")) - { - VERIFY_PERMISSION (OPT_P_GENERAL); - options->http_proxy_fallback = true; - options->force_connection_list = true; - } +#if HTTP_PROXY_OVERRIDE else if (streq (p[0], "http-proxy-override") && p[1] && p[2]) { VERIFY_PERMISSION (OPT_P_GENERAL); @@ -4517,7 +4383,6 @@ add_option (struct options *options, goto err; } re.remote_port = port; - options->ce.port_option_used = true; if (p[3]) { const int proto = ascii2proto (p[3]); @@ -4529,7 +4394,6 @@ add_option (struct options *options, re.proto = proto; } } -#ifdef ENABLE_CONNECTION if (permission_mask & OPT_P_GENERAL) { struct remote_entry *e = alloc_remote_entry (options, msglevel); @@ -4538,7 +4402,6 @@ add_option (struct options *options, *e = re; } else if (permission_mask & OPT_P_CONNECTION) -#endif { connection_entry_load_re (&options->ce, &re); } @@ -4930,7 +4793,6 @@ add_option (struct options *options, msg (msglevel, "Bad port number: %s", p[1]); goto err; } - options->ce.port_option_used = true; options->ce.local_port = options->ce.remote_port = port; } else if (streq (p[0], "lport") && p[1]) @@ -4945,7 +4807,6 @@ add_option (struct options *options, goto err; } options->ce.local_port_defined = true; - options->ce.port_option_used = true; options->ce.local_port = port; } else if (streq (p[0], "rport") && p[1]) @@ -4959,7 +4820,6 @@ add_option (struct options *options, msg (msglevel, "Bad remote port number: %s", p[1]); goto err; } - options->ce.port_option_used = true; options->ce.remote_port = port; } else if (streq (p[0], "bind")) @@ -5011,38 +4871,6 @@ add_option (struct options *options, options->proto_force = proto_force; options->force_connection_list = true; } -#ifdef GENERAL_PROXY_SUPPORT - else if (streq (p[0], "auto-proxy")) - { - char *error = NULL; - - VERIFY_PERMISSION (OPT_P_GENERAL); - options->auto_proxy_info = get_proxy_settings (&error, &options->gc); - if (error) - msg (M_WARN, "PROXY: %s", error); - } - else if (streq (p[0], "show-proxy-settings")) - { - struct auto_proxy_info *pi; - char *error = NULL; - - VERIFY_PERMISSION (OPT_P_GENERAL); - pi = get_proxy_settings (&error, &options->gc); - if (pi) - { - msg (M_INFO|M_NOPREFIX, "HTTP Server: %s", np(pi->http.server)); - msg (M_INFO|M_NOPREFIX, "HTTP Port: %d", pi->http.port); - msg (M_INFO|M_NOPREFIX, "SOCKS Server: %s", np(pi->socks.server)); - msg (M_INFO|M_NOPREFIX, "SOCKS Port: %d", pi->socks.port); - } - if (error) - msg (msglevel, "Proxy error: %s", error); -#ifdef WIN32 - show_win_proxy_settings (M_INFO|M_NOPREFIX); -#endif - openvpn_exit (OPENVPN_EXIT_STATUS_GOOD); /* exit point */ - } -#endif /* GENERAL_PROXY_SUPPORT */ #ifdef ENABLE_HTTP_PROXY else if (streq (p[0], "http-proxy") && p[1]) { @@ -5064,7 +4892,7 @@ add_option (struct options *options, goto err; } - ho = init_http_options_if_undefined (options); + ho = init_http_proxy_options_once (options->ce.http_proxy_options, &options->gc); ho->server = p[1]; ho->port = port; @@ -5099,7 +4927,7 @@ add_option (struct options *options, { struct http_proxy_options *ho; VERIFY_PERMISSION (OPT_P_GENERAL|OPT_P_CONNECTION); - ho = init_http_options_if_undefined (options); + ho = init_http_proxy_options_once (options->ce.http_proxy_options, &options->gc); ho->retry = true; } else if (streq (p[0], "http-proxy-timeout") && p[1]) @@ -5107,7 +4935,7 @@ add_option (struct options *options, struct http_proxy_options *ho; VERIFY_PERMISSION (OPT_P_GENERAL|OPT_P_CONNECTION); - ho = init_http_options_if_undefined (options); + ho = init_http_proxy_options_once (options->ce.http_proxy_options, &options->gc); ho->timeout = positive_atoi (p[1]); } else if (streq (p[0], "http-proxy-option") && p[1]) @@ -5115,7 +4943,7 @@ add_option (struct options *options, struct http_proxy_options *ho; VERIFY_PERMISSION (OPT_P_GENERAL|OPT_P_CONNECTION); - ho = init_http_options_if_undefined (options); + ho = init_http_proxy_options_once (options->ce.http_proxy_options, &options->gc); if (streq (p[1], "VERSION") && p[2]) { @@ -6318,13 +6146,11 @@ add_option (struct options *options, else if (streq (p[0], "secret") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->shared_secret_file_inline = p[2]; } else -#endif if (p[2]) { int key_direction; @@ -6515,12 +6341,10 @@ add_option (struct options *options, { VERIFY_PERMISSION (OPT_P_GENERAL); options->ca_file = p[1]; -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->ca_file_inline = p[2]; } -#endif } #ifndef ENABLE_CRYPTO_POLARSSL else if (streq (p[0], "capath") && p[1]) @@ -6533,34 +6357,28 @@ add_option (struct options *options, { VERIFY_PERMISSION (OPT_P_GENERAL); options->dh_file = p[1]; -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->dh_file_inline = p[2]; } -#endif } else if (streq (p[0], "cert") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); options->cert_file = p[1]; -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->cert_file_inline = p[2]; } -#endif } else if (streq (p[0], "extra-certs") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); options->extra_certs_file = p[1]; -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->extra_certs_file_inline = p[2]; } -#endif } else if (streq (p[0], "verify-hash") && p[1]) { @@ -6578,24 +6396,20 @@ add_option (struct options *options, { VERIFY_PERMISSION (OPT_P_GENERAL); options->priv_key_file = p[1]; -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->priv_key_file_inline = p[2]; } -#endif } #ifndef ENABLE_CRYPTO_POLARSSL else if (streq (p[0], "pkcs12") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); options->pkcs12_file = p[1]; -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->pkcs12_file_inline = p[2]; } -#endif } #endif /* ENABLE_CRYPTO_POLARSSL */ else if (streq (p[0], "askpass")) @@ -6756,13 +6570,11 @@ add_option (struct options *options, else if (streq (p[0], "tls-auth") && p[1]) { VERIFY_PERMISSION (OPT_P_GENERAL); -#if ENABLE_INLINE_FILES if (streq (p[1], INLINE_FILE_TAG) && p[2]) { options->tls_auth_file_inline = p[2]; } else -#endif if (p[2]) { int key_direction; diff --git a/openvpn/src/openvpn/options.h b/openvpn/src/openvpn/options.h index 50d42fb7..306520b0 100644 --- a/openvpn/src/openvpn/options.h +++ b/openvpn/src/openvpn/options.h @@ -90,7 +90,6 @@ struct connection_entry int local_port; bool local_port_defined; int remote_port; - bool port_option_used; const char *local; const char *remote; bool remote_float; @@ -130,11 +129,7 @@ struct connection_entry #endif # define CE_DISABLED (1<<0) -#if HTTP_PROXY_FALLBACK -# define CE_HTTP_PROXY_FALLBACK (1<<1) - time_t ce_http_proxy_fallback_timestamp; /* time when fallback http_proxy_options was last updated */ -#endif -#if MANAGEMENT_QUERY_REMOTE +# define CE_MAN_QUERY_PROXY (1<<1) # define CE_MAN_QUERY_REMOTE_UNDEF 0 # define CE_MAN_QUERY_REMOTE_QUERY 1 # define CE_MAN_QUERY_REMOTE_ACCEPT 2 @@ -142,7 +137,6 @@ struct connection_entry # define CE_MAN_QUERY_REMOTE_SKIP 4 # define CE_MAN_QUERY_REMOTE_MASK (0x07) # define CE_MAN_QUERY_REMOTE_SHIFT (2) -#endif unsigned int flags; }; @@ -153,8 +147,6 @@ struct remote_entry int proto; }; -#ifdef ENABLE_CONNECTION - #define CONNECTION_LIST_SIZE 64 struct connection_list @@ -172,23 +164,11 @@ struct remote_list struct remote_entry *array[CONNECTION_LIST_SIZE]; }; -#endif - -#if HTTP_PROXY_FALLBACK -struct hpo_store -{ - struct http_proxy_options hpo; - char server[80]; -}; -#endif - -#if MANAGEMENT_QUERY_REMOTE struct remote_host_store { # define RH_HOST_LEN 80 char host[RH_HOST_LEN]; }; -#endif /* Command line options */ struct options @@ -224,27 +204,16 @@ struct options /* Networking parms */ struct connection_entry ce; - -#ifdef ENABLE_CONNECTION char *remote_ip_hint; struct connection_list *connection_list; struct remote_list *remote_list; bool force_connection_list; -#endif - -#ifdef GENERAL_PROXY_SUPPORT - struct auto_proxy_info *auto_proxy_info; -#endif -#if HTTP_PROXY_FALLBACK - bool http_proxy_fallback; +#if HTTP_PROXY_OVERRIDE struct http_proxy_options *http_proxy_override; - struct hpo_store *hpo_store; /* used to store dynamic proxy info given by management interface */ #endif -#if MANAGEMENT_QUERY_REMOTE struct remote_host_store *rh_store; -#endif bool remote_random; const char *ipchange; @@ -403,13 +372,13 @@ struct options struct plugin_option_list *plugin_list; #endif -#ifdef ENABLE_TMPDIR - const char *tmp_dir; -#endif + #if P2MP #if P2MP_SERVER + /* the tmp dir is for now only used in the P2P server context */ + const char *tmp_dir; bool server_defined; in_addr_t server_network; in_addr_t server_netmask; @@ -503,9 +472,7 @@ struct options #ifdef ENABLE_CRYPTO /* Cipher parms */ const char *shared_secret_file; -#if ENABLE_INLINE_FILES const char *shared_secret_file_inline; -#endif int key_direction; bool ciphername_defined; const char *ciphername; @@ -543,14 +510,12 @@ struct options const char *tls_remote; const char *crl_file; -#if ENABLE_INLINE_FILES const char *ca_file_inline; const char *cert_file_inline; const char *extra_certs_file_inline; char *priv_key_file_inline; const char *dh_file_inline; const char *pkcs12_file_inline; /* contains the base64 encoding of pkcs12 file */ -#endif int ns_cert_type; /* set to 0, NS_CERT_CHECK_SERVER, or NS_CERT_CHECK_CLIENT */ unsigned remote_cert_ku[MAX_PARMS]; @@ -597,9 +562,7 @@ struct options /* Special authentication MAC for TLS control channel */ const char *tls_auth_file; /* shared secret */ -#if ENABLE_INLINE_FILES const char *tls_auth_file_inline; -#endif /* Allow only one session */ bool single_session; @@ -812,31 +775,14 @@ bool get_ipv6_addr( const char * prefix_str, struct in6_addr *network, static inline bool connection_list_defined (const struct options *o) { -#ifdef ENABLE_CONNECTION return o->connection_list != NULL; -#else - return false; -#endif } static inline void connection_list_set_no_advance (struct options *o) { -#ifdef ENABLE_CONNECTION if (o->connection_list) o->connection_list->no_advance = true; -#endif } -#if HTTP_PROXY_FALLBACK - -struct http_proxy_options * -parse_http_proxy_fallback (struct context *c, - const char *server, - const char *port, - const char *flags, - const int msglevel); - -#endif /* HTTP_PROXY_FALLBACK */ - #endif diff --git a/openvpn/src/openvpn/pkcs11.c b/openvpn/src/openvpn/pkcs11.c index d86e267c..645f1f48 100644 --- a/openvpn/src/openvpn/pkcs11.c +++ b/openvpn/src/openvpn/pkcs11.c @@ -730,7 +730,7 @@ cleanup: } static -bool +PKCS11H_BOOL _pkcs11_openvpn_show_pkcs11_ids_pin_prompt ( void * const global_data, void * const user_data, diff --git a/openvpn/src/openvpn/proxy.c b/openvpn/src/openvpn/proxy.c index 991e165d..28ce019c 100644 --- a/openvpn/src/openvpn/proxy.c +++ b/openvpn/src/openvpn/proxy.c @@ -46,6 +46,21 @@ #define UP_TYPE_PROXY "HTTP Proxy" +struct http_proxy_options * +init_http_proxy_options_once (struct http_proxy_options *hpo, + struct gc_arena *gc) +{ + if (!hpo) + { + ALLOC_OBJ_CLEAR_GC (hpo, struct http_proxy_options, gc); + /* http proxy defaults */ + hpo->timeout = 5; + hpo->http_version = "1.0"; + } + return hpo; +} + + /* cached proxy username/password */ static struct user_pass static_proxy_user_pass; @@ -93,7 +108,7 @@ recv_line (socket_descriptor_t sd, if (status == 0) { if (verbose) - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_line: TCP port read timeout expired"); + msg (D_LINK_ERRORS | M_ERRNO, "recv_line: TCP port read timeout expired"); goto error; } @@ -101,7 +116,7 @@ recv_line (socket_descriptor_t sd, if (status < 0) { if (verbose) - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_line: TCP port read failed on select()"); + msg (D_LINK_ERRORS | M_ERRNO, "recv_line: TCP port read failed on select()"); goto error; } @@ -112,7 +127,7 @@ recv_line (socket_descriptor_t sd, if (size != 1) { if (verbose) - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_line: TCP port read failed on recv()"); + msg (D_LINK_ERRORS | M_ERRNO, "recv_line: TCP port read failed on recv()"); goto error; } @@ -137,7 +152,7 @@ recv_line (socket_descriptor_t sd, if (!isprint(c) && !isspace(c)) /* not ascii? */ { if (verbose) - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_line: Non-ASCII character (%d) read on recv()", (int)c); + msg (D_LINK_ERRORS | M_ERRNO, "recv_line: Non-ASCII character (%d) read on recv()", (int)c); *lookahead = la; return false; } @@ -167,7 +182,7 @@ send_line (socket_descriptor_t sd, const ssize_t size = send (sd, buf, strlen (buf), MSG_NOSIGNAL); if (size != (ssize_t) strlen (buf)) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "send_line: TCP port write failed on send()"); + msg (D_LINK_ERRORS | M_ERRNO, "send_line: TCP port write failed on send()"); return false; } return true; @@ -421,47 +436,11 @@ get_pa_var (const char *key, const char *pa, struct gc_arena *gc) } struct http_proxy_info * -http_proxy_new (const struct http_proxy_options *o, - struct auto_proxy_info *auto_proxy_info) +http_proxy_new (const struct http_proxy_options *o) { struct http_proxy_info *p; struct http_proxy_options opt; - if (auto_proxy_info) - { - if (o && o->server) - { - /* if --http-proxy explicitly given, disable auto-proxy */ - auto_proxy_info = NULL; - } - else - { - /* if no --http-proxy explicitly given and no auto settings, fail */ - if (!auto_proxy_info->http.server) - return NULL; - - if (o) - { - opt = *o; - } - else - { - CLEAR (opt); - - /* These settings are only used for --auto-proxy */ - opt.timeout = 5; - opt.http_version = "1.0"; - } - - opt.server = auto_proxy_info->http.server; - opt.port = auto_proxy_info->http.port; - if (!opt.auth_retry) - opt.auth_retry = PAR_ALL; - - o = &opt; - } - } - if (!o || !o->server) msg (M_FATAL, "HTTP_PROXY: server not specified"); @@ -527,7 +506,7 @@ establish_http_proxy_passthru (struct http_proxy_info *p, bool ret = false; bool processed = false; - /* get user/pass if not previously given or if --auto-proxy is being used */ + /* get user/pass if not previously given */ if (p->auth_method == HTTP_AUTH_BASIC || p->auth_method == HTTP_AUTH_DIGEST || p->auth_method == HTTP_AUTH_NTLM) @@ -926,205 +905,3 @@ establish_http_proxy_passthru (struct http_proxy_info *p, static void dummy(void) {} #endif /* ENABLE_HTTP_PROXY */ -#ifdef GENERAL_PROXY_SUPPORT - -#ifdef WIN32 - -#if 0 -char * -get_windows_internet_string (const DWORD dwOption, struct gc_arena *gc) -{ - DWORD size = 0; - char *ret = NULL; - - /* Initially, get size of return buffer */ - InternetQueryOption (NULL, dwOption, NULL, &size); - if (size) - { - /* Now get actual info */ - ret = (INTERNET_PROXY_INFO *) gc_malloc (size, false, gc); - if (!InternetQueryOption (NULL, dwOption, (LPVOID) ret, &size)) - ret = NULL; - } - return ret; -} -#endif - -static INTERNET_PROXY_INFO * -get_windows_proxy_settings (struct gc_arena *gc) -{ - DWORD size = 0; - INTERNET_PROXY_INFO *ret = NULL; - - /* Initially, get size of return buffer */ - InternetQueryOption (NULL, INTERNET_OPTION_PROXY, NULL, &size); - if (size) - { - /* Now get actual info */ - ret = (INTERNET_PROXY_INFO *) gc_malloc (size, false, gc); - if (!InternetQueryOption (NULL, INTERNET_OPTION_PROXY, (LPVOID) ret, &size)) - ret = NULL; - } - return ret; -} - -static const char * -parse_windows_proxy_setting (const char *str, struct auto_proxy_info_entry *e, struct gc_arena *gc) -{ - char buf[128]; - const char *ret = NULL; - struct buffer in; - - CLEAR (*e); - - buf_set_read (&in, (const uint8_t *)str, strlen (str)); - - if (strchr (str, '=') != NULL) - { - if (buf_parse (&in, '=', buf, sizeof (buf))) - ret = string_alloc (buf, gc); - } - - if (buf_parse (&in, ':', buf, sizeof (buf))) - e->server = string_alloc (buf, gc); - - if (e->server && buf_parse (&in, '\0', buf, sizeof (buf))) - e->port = atoi (buf); - - return ret; -} - -static void -parse_windows_proxy_setting_list (const char *str, const char *type, struct auto_proxy_info_entry *e, struct gc_arena *gc) -{ - struct gc_arena gc_local = gc_new (); - struct auto_proxy_info_entry el; - - CLEAR (*e); - if (type) - { - char buf[128]; - struct buffer in; - - buf_set_read (&in, (const uint8_t *)str, strlen (str)); - if (strchr (str, '=') != NULL) - { - while (buf_parse (&in, ' ', buf, sizeof (buf))) - { - const char *t = parse_windows_proxy_setting (buf, &el, &gc_local); - if (t && !strcmp (t, type)) - goto found; - } - } - } - else - { - if (!parse_windows_proxy_setting (str, &el, &gc_local)) - goto found; - } - goto done; - - found: - if (el.server && el.port > 0) - { - e->server = string_alloc (el.server, gc); - e->port = el.port; - } - - done: - gc_free (&gc_local); -} - -static const char * -win_proxy_access_type (const DWORD dwAccessType) -{ - switch (dwAccessType) - { - case INTERNET_OPEN_TYPE_DIRECT: - return "INTERNET_OPEN_TYPE_DIRECT"; - case INTERNET_OPEN_TYPE_PROXY: - return "INTERNET_OPEN_TYPE_PROXY"; - default: - return "[UNKNOWN]"; - } -} - -void -show_win_proxy_settings (const int msglevel) -{ - INTERNET_PROXY_INFO *info; - struct gc_arena gc = gc_new (); - - info = get_windows_proxy_settings (&gc); - msg (msglevel, "PROXY INFO: %s %s", - win_proxy_access_type (info->dwAccessType), - info->lpszProxy ? info->lpszProxy : "[NULL]"); - - gc_free (&gc); -} - -struct auto_proxy_info * -get_proxy_settings (char **err, struct gc_arena *gc) -{ - struct gc_arena gc_local = gc_new (); - INTERNET_PROXY_INFO *info; - struct auto_proxy_info *pi; - - ALLOC_OBJ_CLEAR_GC (pi, struct auto_proxy_info, gc); - - if (err) - *err = NULL; - - info = get_windows_proxy_settings (&gc_local); - - if (!info) - { - if (err) - *err = "PROXY: failed to obtain windows proxy info"; - goto done; - } - - switch (info->dwAccessType) - { - case INTERNET_OPEN_TYPE_DIRECT: - break; - case INTERNET_OPEN_TYPE_PROXY: - if (!info->lpszProxy) - break; - parse_windows_proxy_setting_list (info->lpszProxy, NULL, &pi->http, gc); - if (!pi->http.server) - parse_windows_proxy_setting_list (info->lpszProxy, "http", &pi->http, gc); - parse_windows_proxy_setting_list (info->lpszProxy, "socks", &pi->socks, gc); - break; - default: - if (err) - *err = "PROXY: unknown proxy type"; - break; - } - - done: - gc_free (&gc_local); - return pi; -} - -#else - -struct auto_proxy_info * -get_proxy_settings (char **err, struct gc_arena *gc) -{ -#if 1 - if (err) - *err = string_alloc ("PROXY: automatic detection not supported on this OS", gc); - return NULL; -#else /* test --auto-proxy feature */ - struct auto_proxy_info *pi; - ALLOC_OBJ_CLEAR_GC (pi, struct auto_proxy_info, gc); - pi->http.server = "10.10.0.2"; - pi->http.port = 4000; - return pi; -#endif -} - -#endif - -#endif /* GENERAL_PROXY_SUPPORT */ diff --git a/openvpn/src/openvpn/proxy.h b/openvpn/src/openvpn/proxy.h index d89aa4af..dc62261c 100644 --- a/openvpn/src/openvpn/proxy.h +++ b/openvpn/src/openvpn/proxy.h @@ -28,30 +28,6 @@ #include "buffer.h" #include "misc.h" -#ifdef GENERAL_PROXY_SUPPORT - -/* - * Return value for get_proxy_settings to automatically - * determine proxy information. - */ -struct auto_proxy_info_entry { - char *server; - int port; -}; - -struct auto_proxy_info { - struct auto_proxy_info_entry http; - struct auto_proxy_info_entry socks; -}; - -struct auto_proxy_info *get_proxy_settings (char **err, struct gc_arena *gc); - -#ifdef WIN32 -void show_win_proxy_settings (const int msglevel); -#endif /* WIN32 */ - -#endif /* GENERAL_PROXY_SUPPORT */ - #ifdef ENABLE_HTTP_PROXY /* HTTP CONNECT authentication methods */ @@ -94,8 +70,10 @@ struct http_proxy_info { bool queried_creds; }; -struct http_proxy_info *http_proxy_new (const struct http_proxy_options *o, - struct auto_proxy_info *auto_proxy_info); +struct http_proxy_options *init_http_proxy_options_once (struct http_proxy_options *hpo, + struct gc_arena *gc); + +struct http_proxy_info *http_proxy_new (const struct http_proxy_options *o); void http_proxy_close (struct http_proxy_info *hp); diff --git a/openvpn/src/openvpn/ps.c b/openvpn/src/openvpn/ps.c index 5d056eed..6495dc71 100644 --- a/openvpn/src/openvpn/ps.c +++ b/openvpn/src/openvpn/ps.c @@ -233,7 +233,7 @@ port_share_sendmsg (const socket_descriptor_t sd, status = sendmsg (sd, &mesg, MSG_NOSIGNAL); if (status == -1) - msg (M_WARN|M_ERRNO_SOCK, "PORT SHARE: sendmsg failed -- unable to communicate with background process (%d,%d,%d,%d)", + msg (M_WARN|M_ERRNO, "PORT SHARE: sendmsg failed -- unable to communicate with background process (%d,%d,%d,%d)", sd, sd_send, sd_null[0], sd_null[1] ); @@ -419,7 +419,7 @@ proxy_entry_new (struct proxy_connection **list, sock_addr_set (&osaddr, server_addr, server_port); if ((sd_server = socket (PF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) { - msg (M_WARN|M_ERRNO_SOCK, "PORT SHARE PROXY: cannot create socket"); + msg (M_WARN|M_ERRNO, "PORT SHARE PROXY: cannot create socket"); return false; } status = openvpn_connect (sd_server, &osaddr, 5, NULL); @@ -851,7 +851,7 @@ port_share_open (const char *host, } else { - msg (M_SOCKERR, "PORT SHARE: unexpected init recv_control status=%d", status); + msg (M_ERR, "PORT SHARE: unexpected init recv_control status=%d", status); } } else diff --git a/openvpn/src/openvpn/route.c b/openvpn/src/openvpn/route.c index 7c02d6f5..e908be99 100644 --- a/openvpn/src/openvpn/route.c +++ b/openvpn/src/openvpn/route.c @@ -383,7 +383,6 @@ init_route_ipv6 (struct route_ipv6 *r6, const struct route_ipv6_option *r6o, const struct route_ipv6_list *rl6 ) { - r6->option = r6o; r6->defined = false; if ( !get_ipv6_addr( r6o->prefix, &r6->network, &r6->netbits, NULL, M_WARN )) @@ -410,7 +409,7 @@ init_route_ipv6 (struct route_ipv6 *r6, /* metric */ r6->metric_defined = false; - r6->metric = 0; + r6->metric = -1; if (is_route_parm_defined (r6o->metric)) { r6->metric = atoi (r6o->metric); @@ -700,7 +699,7 @@ init_route_ipv6_list (struct route_ipv6_list *rl6, rl6->flags = opt6->flags; - if (default_metric) + if (default_metric >= 0 ) { rl6->default_metric = default_metric; rl6->default_metric_defined = true; @@ -1562,6 +1561,8 @@ add_route_ipv6 (struct route_ipv6 *r6, const struct tuntap *tt, unsigned int fla bool status = false; const char *device = tt->actual_name; + bool gateway_needed = false; + if (!r6->defined) return; @@ -1586,6 +1587,18 @@ add_route_ipv6 (struct route_ipv6 *r6, const struct tuntap *tt, unsigned int fla * (not currently done for IPv6) */ + /* On "tun" interface, we never set a gateway if the operating system + * can do "route to interface" - it does not add value, as the target + * dev already fully qualifies the route destination on point-to-point + * interfaces. OTOH, on "tap" interface, we must always set the + * gateway unless the route is to be an on-link network + */ + if ( tt->type == DEV_TYPE_TAP && + !(r6->metric_defined && r6->metric == 0 ) ) + { + gateway_needed = true; + } + #if defined(TARGET_LINUX) #ifdef ENABLE_IPROUTE argv_printf (&argv, "%s -6 route add %s/%d dev %s", @@ -1593,7 +1606,9 @@ add_route_ipv6 (struct route_ipv6 *r6, const struct tuntap *tt, unsigned int fla network, r6->netbits, device); - if (r6->metric_defined) + if (gateway_needed) + argv_printf_cat (&argv, "via %s", gateway); + if (r6->metric_defined && r6->metric > 0 ) argv_printf_cat (&argv, " metric %d", r6->metric); #else @@ -1602,7 +1617,9 @@ add_route_ipv6 (struct route_ipv6 *r6, const struct tuntap *tt, unsigned int fla network, r6->netbits, device); - if (r6->metric_defined) + if (gateway_needed) + argv_printf_cat (&argv, "gw %s", gateway); + if (r6->metric_defined && r6->metric > 0 ) argv_printf_cat (&argv, " metric %d", r6->metric); #endif /*ENABLE_IPROUTE*/ argv_msg (D_ROUTE, &argv); @@ -1673,20 +1690,29 @@ add_route_ipv6 (struct route_ipv6 *r6, const struct tuntap *tt, unsigned int fla #elif defined(TARGET_FREEBSD) || defined(TARGET_DRAGONFLY) - argv_printf (&argv, "%s add -inet6 %s/%d -iface %s", + argv_printf (&argv, "%s add -inet6 %s/%d", ROUTE_PATH, network, - r6->netbits, - device ); + r6->netbits); + + if (gateway_needed) + argv_printf_cat (&argv, "%s", gateway); + else + argv_printf_cat (&argv, "-iface %s", device); argv_msg (D_ROUTE, &argv); status = openvpn_execve_check (&argv, es, 0, "ERROR: *BSD route add -inet6 command failed"); #elif defined(TARGET_DARWIN) - argv_printf (&argv, "%s add -inet6 %s -prefixlen %d -iface %s", + argv_printf (&argv, "%s add -inet6 %s -prefixlen %d", ROUTE_PATH, - network, r6->netbits, device ); + network, r6->netbits ); + + if (gateway_needed) + argv_printf_cat (&argv, "%s", gateway); + else + argv_printf_cat (&argv, "-iface %s", device); argv_msg (D_ROUTE, &argv); status = openvpn_execve_check (&argv, es, 0, "ERROR: MacOS X route add -inet6 command failed"); @@ -1887,6 +1913,7 @@ delete_route_ipv6 (const struct route_ipv6 *r6, const struct tuntap *tt, unsigne const char *network; const char *gateway; const char *device = tt->actual_name; + bool gateway_needed = false; if (!r6->defined) return; @@ -1906,6 +1933,16 @@ delete_route_ipv6 (const struct route_ipv6 *r6, const struct tuntap *tt, unsigne msg( M_INFO, "delete_route_ipv6(%s/%d)", network, r6->netbits ); + /* if we used a gateway on "add route", we also need to specify it on + * delete, otherwise some OSes will refuse to delete the route + */ + if ( tt->type == DEV_TYPE_TAP && + !(r6->metric_defined && r6->metric == 0 ) ) + { + gateway_needed = true; + } + + #if defined(TARGET_LINUX) #ifdef ENABLE_IPROUTE argv_printf (&argv, "%s -6 route del %s/%d dev %s", @@ -1913,12 +1950,18 @@ delete_route_ipv6 (const struct route_ipv6 *r6, const struct tuntap *tt, unsigne network, r6->netbits, device); + if (gateway_needed) + argv_printf_cat (&argv, "via %s", gateway); #else argv_printf (&argv, "%s -A inet6 del %s/%d dev %s", ROUTE_PATH, network, r6->netbits, device); + if (gateway_needed) + argv_printf_cat (&argv, "gw %s", gateway); + if (r6->metric_defined && r6->metric > 0 ) + argv_printf_cat (&argv, " metric %d", r6->metric); #endif /*ENABLE_IPROUTE*/ argv_msg (D_ROUTE, &argv); openvpn_execve_check (&argv, es, 0, "ERROR: Linux route -6/-A inet6 del command failed"); @@ -1971,23 +2014,32 @@ delete_route_ipv6 (const struct route_ipv6 *r6, const struct tuntap *tt, unsigne #elif defined(TARGET_FREEBSD) || defined(TARGET_DRAGONFLY) - argv_printf (&argv, "%s delete -inet6 %s/%d -iface %s", + argv_printf (&argv, "%s delete -inet6 %s/%d", ROUTE_PATH, network, - r6->netbits, - device ); + r6->netbits ); + + if (gateway_needed) + argv_printf_cat (&argv, "%s", gateway); + else + argv_printf_cat (&argv, "-iface %s", device); argv_msg (D_ROUTE, &argv); openvpn_execve_check (&argv, es, 0, "ERROR: *BSD route delete -inet6 command failed"); #elif defined(TARGET_DARWIN) - argv_printf (&argv, "%s delete -inet6 %s -prefixlen %d -iface %s", + argv_printf (&argv, "%s delete -inet6 %s -prefixlen %d", ROUTE_PATH, - network, r6->netbits, device ); + network, r6->netbits ); + + if (gateway_needed) + argv_printf_cat (&argv, "%s", gateway); + else + argv_printf_cat (&argv, "-iface %s", device); argv_msg (D_ROUTE, &argv); - openvpn_execve_check (&argv, es, 0, "ERROR: *BSD route delete -inet6 command failed"); + openvpn_execve_check (&argv, es, 0, "ERROR: MacOS X route delete -inet6 command failed"); #elif defined(TARGET_OPENBSD) diff --git a/openvpn/src/openvpn/route.h b/openvpn/src/openvpn/route.h index c0f5f574..e63db595 100644 --- a/openvpn/src/openvpn/route.h +++ b/openvpn/src/openvpn/route.h @@ -124,7 +124,6 @@ struct route { struct route_ipv6 { bool defined; - const struct route_ipv6_option *option; struct in6_addr network; unsigned int netbits; struct in6_addr gateway; diff --git a/openvpn/src/openvpn/socket.c b/openvpn/src/openvpn/socket.c index d417172a..339470b0 100644 --- a/openvpn/src/openvpn/socket.c +++ b/openvpn/src/openvpn/socket.c @@ -835,7 +835,7 @@ create_socket_tcp (void) socket_descriptor_t sd; if ((sd = socket (PF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) - msg (M_SOCKERR, "Cannot create TCP socket"); + msg (M_ERR, "Cannot create TCP socket"); #ifndef WIN32 /* using SO_REUSEADDR on Windows will cause bind to succeed on port conflicts! */ /* set SO_REUSEADDR on socket */ @@ -843,7 +843,7 @@ create_socket_tcp (void) int on = 1; if (setsockopt (sd, SOL_SOCKET, SO_REUSEADDR, (void *) &on, sizeof (on)) < 0) - msg (M_SOCKERR, "TCP: Cannot setsockopt SO_REUSEADDR on TCP socket"); + msg (M_ERR, "TCP: Cannot setsockopt SO_REUSEADDR on TCP socket"); } #endif @@ -855,7 +855,7 @@ create_socket_tcp (void) linger.l_linger = 2; if (setsockopt (sd, SOL_SOCKET, SO_LINGER, (void *) &linger, sizeof (linger)) < 0) - msg (M_SOCKERR, "TCP: Cannot setsockopt SO_LINGER on TCP socket"); + msg (M_ERR, "TCP: Cannot setsockopt SO_LINGER on TCP socket"); } #endif @@ -868,7 +868,7 @@ create_socket_udp (const unsigned int flags) socket_descriptor_t sd; if ((sd = socket (PF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0) - msg (M_SOCKERR, "UDP: Cannot create UDP socket"); + msg (M_ERR, "UDP: Cannot create UDP socket"); #if ENABLE_IP_PKTINFO else if (flags & SF_USE_IP_PKTINFO) { @@ -876,11 +876,11 @@ create_socket_udp (const unsigned int flags) #ifdef IP_PKTINFO if (setsockopt (sd, SOL_IP, IP_PKTINFO, (void*)&pad, sizeof(pad)) < 0) - msg(M_SOCKERR, "UDP: failed setsockopt for IP_PKTINFO"); + msg(M_ERR, "UDP: failed setsockopt for IP_PKTINFO"); #elif defined(IP_RECVDSTADDR) if (setsockopt (sd, IPPROTO_IP, IP_RECVDSTADDR, (void*)&pad, sizeof(pad)) < 0) - msg(M_SOCKERR, "UDP: failed setsockopt for IP_RECVDSTADDR"); + msg(M_ERR, "UDP: failed setsockopt for IP_RECVDSTADDR"); #else #error ENABLE_IP_PKTINFO is set without IP_PKTINFO xor IP_RECVDSTADDR (fix syshead.h) #endif @@ -895,14 +895,19 @@ create_socket_udp6 (const unsigned int flags) socket_descriptor_t sd; if ((sd = socket (PF_INET6, SOCK_DGRAM, IPPROTO_UDP)) < 0) - msg (M_SOCKERR, "UDP: Cannot create UDP6 socket"); + msg (M_ERR, "UDP: Cannot create UDP6 socket"); #if ENABLE_IP_PKTINFO else if (flags & SF_USE_IP_PKTINFO) { int pad = 1; +#ifndef IPV6_RECVPKTINFO /* Some older Darwin platforms require this */ + if (setsockopt (sd, IPPROTO_IPV6, IPV6_PKTINFO, + (void*)&pad, sizeof(pad)) < 0) +#else if (setsockopt (sd, IPPROTO_IPV6, IPV6_RECVPKTINFO, (void*)&pad, sizeof(pad)) < 0) - msg(M_SOCKERR, "UDP: failed setsockopt for IPV6_RECVPKTINFO"); +#endif + msg(M_ERR, "UDP: failed setsockopt for IPV6_RECVPKTINFO"); } #endif return sd; @@ -914,14 +919,14 @@ create_socket_tcp6 (void) socket_descriptor_t sd; if ((sd = socket (PF_INET6, SOCK_STREAM, IPPROTO_TCP)) < 0) - msg (M_SOCKERR, "Cannot create TCP6 socket"); + msg (M_ERR, "Cannot create TCP6 socket"); /* set SO_REUSEADDR on socket */ { int on = 1; if (setsockopt (sd, SOL_SOCKET, SO_REUSEADDR, (void *) &on, sizeof (on)) < 0) - msg (M_SOCKERR, "TCP: Cannot setsockopt SO_REUSEADDR on TCP6 socket"); + msg (M_ERR, "TCP: Cannot setsockopt SO_REUSEADDR on TCP6 socket"); } return sd; @@ -987,7 +992,7 @@ socket_do_listen (socket_descriptor_t sd, msg (M_INFO, "Listening for incoming TCP connection on %s", print_sockaddr (local, &gc)); if (listen (sd, 1)) - msg (M_SOCKERR, "TCP: listen() failed"); + msg (M_ERR, "TCP: listen() failed"); } /* set socket to non-blocking mode */ @@ -1018,7 +1023,7 @@ socket_do_accept (socket_descriptor_t sd, new_sd = getpeername (sd, &act->dest.addr.sa, &remote_len); if (!socket_defined (new_sd)) - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "TCP: getpeername() failed"); + msg (D_LINK_ERRORS | M_ERRNO, "TCP: getpeername() failed"); else new_sd = sd; } @@ -1042,7 +1047,7 @@ socket_do_accept (socket_descriptor_t sd, if (!socket_defined (new_sd)) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "TCP: accept(%d) failed", sd); + msg (D_LINK_ERRORS | M_ERRNO, "TCP: accept(%d) failed", sd); } /* only valid if we have remote_len_af!=0 */ else if (remote_len_af && remote_len != remote_len_af) @@ -1102,7 +1107,7 @@ socket_listen_accept (socket_descriptor_t sd, } if (status < 0) - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "TCP: select() failed"); + msg (D_LINK_ERRORS | M_ERRNO, "TCP: select() failed"); if (status <= 0) { @@ -1122,7 +1127,7 @@ socket_listen_accept (socket_descriptor_t sd, "TCP NOTE: Rejected connection attempt from %s due to --remote setting", print_link_socket_actual (act, &gc)); if (openvpn_close_socket (new_sd)) - msg (M_SOCKERR, "TCP: close socket failed (new_sd)"); + msg (M_ERR, "TCP: close socket failed (new_sd)"); } else break; @@ -1131,7 +1136,7 @@ socket_listen_accept (socket_descriptor_t sd, } if (!nowait && openvpn_close_socket (sd)) - msg (M_SOCKERR, "TCP: close socket failed (sd)"); + msg (M_ERR, "TCP: close socket failed (sd)"); tcp_connection_established (act); @@ -1148,7 +1153,7 @@ socket_bind (socket_descriptor_t sd, if (bind (sd, &local->addr.sa, af_addr_size(local->addr.sa.sa_family))) { - const int errnum = openvpn_errno_socket (); + const int errnum = openvpn_errno (); msg (M_FATAL, "%s: Socket bind failed on local address %s: %s", prefix, print_sockaddr (local, &gc), @@ -1169,8 +1174,14 @@ openvpn_connect (socket_descriptor_t sd, set_nonblock (sd); status = connect (sd, &remote->addr.sa, af_addr_size(remote->addr.sa.sa_family)); if (status) - status = openvpn_errno_socket (); - if (status == EINPROGRESS) + status = openvpn_errno (); + if ( +#ifdef WIN32 + status == WSAEWOULDBLOCK +#else + status == EINPROGRESS +#endif + ) { while (true) { @@ -1195,7 +1206,7 @@ openvpn_connect (socket_descriptor_t sd, } if (status < 0) { - status = openvpn_errno_socket (); + status = openvpn_errno (); break; } if (status <= 0) @@ -1219,7 +1230,7 @@ openvpn_connect (socket_descriptor_t sd, && len == sizeof (val)) status = val; else - status = openvpn_errno_socket (); + status = openvpn_errno (); break; } } @@ -1227,7 +1238,7 @@ openvpn_connect (socket_descriptor_t sd, #else status = connect (sd, &remote->addr.sa, af_addr_size(remote->addr.sa.sa_family)); if (status) - status = openvpn_errno_socket (); + status = openvpn_errno (); #endif return status; @@ -2045,7 +2056,7 @@ link_socket_close (struct link_socket *sock) { msg (D_LOW, "TCP/UDP: Closing socket"); if (openvpn_close_socket (sock->sd)) - msg (M_WARN | M_ERRNO_SOCK, "TCP/UDP: Close Socket failed"); + msg (M_WARN | M_ERRNO, "TCP/UDP: Close Socket failed"); } sock->sd = SOCKET_UNDEFINED; #ifdef WIN32 @@ -2061,7 +2072,7 @@ link_socket_close (struct link_socket *sock) if (socket_defined (sock->ctrl_sd)) { if (openvpn_close_socket (sock->ctrl_sd)) - msg (M_WARN | M_ERRNO_SOCK, "TCP/UDP: Close Socket (ctrl_sd) failed"); + msg (M_WARN | M_ERRNO, "TCP/UDP: Close Socket (ctrl_sd) failed"); sock->ctrl_sd = SOCKET_UNDEFINED; } #endif @@ -3353,7 +3364,7 @@ socket_finalize (SOCKET s, /* if no error (i.e. just not finished yet), then DON'T execute this code */ io->iostate = IOSTATE_INITIAL; ASSERT (ResetEvent (io->overlapped.hEvent)); - msg (D_WIN32_IO | M_ERRNO_SOCK, "WIN32 I/O: Socket Completion error"); + msg (D_WIN32_IO | M_ERRNO, "WIN32 I/O: Socket Completion error"); } } break; @@ -3366,7 +3377,7 @@ socket_finalize (SOCKET s, /* error return for a non-queued operation */ WSASetLastError (io->status); ret = -1; - msg (D_WIN32_IO | M_ERRNO_SOCK, "WIN32 I/O: Socket Completion non-queued error"); + msg (D_WIN32_IO | M_ERRNO, "WIN32 I/O: Socket Completion non-queued error"); } else { @@ -3500,7 +3511,7 @@ create_socket_unix (void) socket_descriptor_t sd; if ((sd = socket (PF_UNIX, SOCK_STREAM, 0)) < 0) - msg (M_SOCKERR, "Cannot create unix domain socket"); + msg (M_ERR, "Cannot create unix domain socket"); return sd; } @@ -3517,7 +3528,7 @@ socket_bind_unix (socket_descriptor_t sd, if (bind (sd, (struct sockaddr *) local, sizeof (struct sockaddr_un))) { - const int errnum = openvpn_errno_socket (); + const int errnum = openvpn_errno (); msg (M_FATAL, "%s: Socket bind[%d] failed on unix domain socket %s: %s", prefix, (int)sd, @@ -3550,7 +3561,7 @@ socket_connect_unix (socket_descriptor_t sd, { int status = connect (sd, (struct sockaddr *) remote, sizeof (struct sockaddr_un)); if (status) - status = openvpn_errno_socket (); + status = openvpn_errno (); return status; } diff --git a/openvpn/src/openvpn/socket.h b/openvpn/src/openvpn/socket.h index ef21cb61..47c6e8eb 100644 --- a/openvpn/src/openvpn/socket.h +++ b/openvpn/src/openvpn/socket.h @@ -750,7 +750,7 @@ socket_connection_reset (const struct link_socket *sock, int status) return true; else if (status < 0) { - const int err = openvpn_errno_socket (); + const int err = openvpn_errno (); #ifdef WIN32 return err == WSAECONNRESET || err == WSAECONNABORTED; #else diff --git a/openvpn/src/openvpn/socks.c b/openvpn/src/openvpn/socks.c index 510c1102..235982e4 100644 --- a/openvpn/src/openvpn/socks.c +++ b/openvpn/src/openvpn/socks.c @@ -63,23 +63,10 @@ struct socks_proxy_info * socks_proxy_new (const char *server, int port, const char *authfile, - bool retry, - struct auto_proxy_info *auto_proxy_info) + bool retry) { struct socks_proxy_info *p; - if (auto_proxy_info) - { - if (!server) - { - if (!auto_proxy_info->socks.server) - return NULL; - - server = auto_proxy_info->socks.server; - port = auto_proxy_info->socks.port; - } - } - ALLOC_OBJ_CLEAR (p, struct socks_proxy_info); ASSERT (server); @@ -133,7 +120,7 @@ socks_username_password_auth (struct socks_proxy_info *p, if (size != strlen (to_send)) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_username_password_auth: TCP port write failed on send()"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_username_password_auth: TCP port write failed on send()"); return false; } @@ -159,14 +146,14 @@ socks_username_password_auth (struct socks_proxy_info *p, /* timeout? */ if (status == 0) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_username_password_auth: TCP port read timeout expired"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_username_password_auth: TCP port read timeout expired"); return false; } /* error */ if (status < 0) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_username_password_auth: TCP port read failed on select()"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_username_password_auth: TCP port read failed on select()"); return false; } @@ -176,7 +163,7 @@ socks_username_password_auth (struct socks_proxy_info *p, /* error? */ if (size != 1) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_username_password_auth: TCP port read failed on recv()"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_username_password_auth: TCP port read failed on recv()"); return false; } @@ -207,7 +194,7 @@ socks_handshake (struct socks_proxy_info *p, const ssize_t size = send (sd, "\x05\x02\x00\x02", 4, MSG_NOSIGNAL); if (size != 4) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_handshake: TCP port write failed on send()"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_handshake: TCP port write failed on send()"); return false; } @@ -233,14 +220,14 @@ socks_handshake (struct socks_proxy_info *p, /* timeout? */ if (status == 0) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_handshake: TCP port read timeout expired"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_handshake: TCP port read timeout expired"); return false; } /* error */ if (status < 0) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_handshake: TCP port read failed on select()"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_handshake: TCP port read failed on select()"); return false; } @@ -250,7 +237,7 @@ socks_handshake (struct socks_proxy_info *p, /* error? */ if (size != 1) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "socks_handshake: TCP port read failed on recv()"); + msg (D_LINK_ERRORS | M_ERRNO, "socks_handshake: TCP port read failed on recv()"); return false; } @@ -332,14 +319,14 @@ recv_socks_reply (socket_descriptor_t sd, /* timeout? */ if (status == 0) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_socks_reply: TCP port read timeout expired"); + msg (D_LINK_ERRORS | M_ERRNO, "recv_socks_reply: TCP port read timeout expired"); return false; } /* error */ if (status < 0) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_socks_reply: TCP port read failed on select()"); + msg (D_LINK_ERRORS | M_ERRNO, "recv_socks_reply: TCP port read failed on select()"); return false; } @@ -349,7 +336,7 @@ recv_socks_reply (socket_descriptor_t sd, /* error? */ if (size != 1) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "recv_socks_reply: TCP port read failed on recv()"); + msg (D_LINK_ERRORS | M_ERRNO, "recv_socks_reply: TCP port read failed on recv()"); return false; } @@ -434,7 +421,7 @@ establish_socks_proxy_passthru (struct socks_proxy_info *p, const ssize_t size = send (sd, buf, 5 + len + 2, MSG_NOSIGNAL); if ((int)size != 5 + (int)len + 2) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "establish_socks_proxy_passthru: TCP port write failed on send()"); + msg (D_LINK_ERRORS | M_ERRNO, "establish_socks_proxy_passthru: TCP port write failed on send()"); goto error; } } @@ -471,7 +458,7 @@ establish_socks_proxy_udpassoc (struct socks_proxy_info *p, 10, MSG_NOSIGNAL); if (size != 10) { - msg (D_LINK_ERRORS | M_ERRNO_SOCK, "establish_socks_proxy_passthru: TCP port write failed on send()"); + msg (D_LINK_ERRORS | M_ERRNO, "establish_socks_proxy_passthru: TCP port write failed on send()"); goto error; } } diff --git a/openvpn/src/openvpn/socks.h b/openvpn/src/openvpn/socks.h index b748bb3f..b55ff6fb 100644 --- a/openvpn/src/openvpn/socks.h +++ b/openvpn/src/openvpn/socks.h @@ -51,8 +51,7 @@ void socks_adjust_frame_parameters (struct frame *frame, int proto); struct socks_proxy_info *socks_proxy_new (const char *server, int port, const char *authfile, - bool retry, - struct auto_proxy_info *auto_proxy_info); + bool retry); void socks_proxy_close (struct socks_proxy_info *sp); diff --git a/openvpn/src/openvpn/ssl_backend.h b/openvpn/src/openvpn/ssl_backend.h index f3e69dd3..203a4d26 100644 --- a/openvpn/src/openvpn/ssl_backend.h +++ b/openvpn/src/openvpn/ssl_backend.h @@ -138,11 +138,8 @@ void tls_ctx_restrict_ciphers(struct tls_root_ctx *ctx, const char *ciphers); * "[[INLINE]]" in the case of inline files. * @param dh_file_inline A string containing the parameters */ -void tls_ctx_load_dh_params(struct tls_root_ctx *ctx, const char *dh_file -#if ENABLE_INLINE_FILES - , const char *dh_file_inline -#endif /* ENABLE_INLINE_FILES */ - ); +void tls_ctx_load_dh_params(struct tls_root_ctx *ctx, const char *dh_file, + const char *dh_file_inline); /** * Load PKCS #12 file for key, cert and (optionally) CA certs, and add to @@ -157,10 +154,7 @@ void tls_ctx_load_dh_params(struct tls_root_ctx *ctx, const char *dh_file * successful. */ int tls_ctx_load_pkcs12(struct tls_root_ctx *ctx, const char *pkcs12_file, -#if ENABLE_INLINE_FILES - const char *pkcs12_file_inline, -#endif /* ENABLE_INLINE_FILES */ - bool load_ca_file + const char *pkcs12_file_inline, bool load_ca_file ); /** @@ -190,10 +184,7 @@ void tls_ctx_load_cryptoapi(struct tls_root_ctx *ctx, const char *cryptoapi_cert * *x509 must be NULL. */ void tls_ctx_load_cert_file (struct tls_root_ctx *ctx, const char *cert_file, -#if ENABLE_INLINE_FILES - const char *cert_file_inline, -#endif - openvpn_x509_cert_t **x509 + const char *cert_file_inline, openvpn_x509_cert_t **x509 ); /** @@ -214,10 +205,8 @@ void tls_ctx_free_cert_file (openvpn_x509_cert_t *x509); * @return 1 if an error occurred, 0 if parsing was * successful. */ -int tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file -#if ENABLE_INLINE_FILES - , const char *priv_key_file_inline -#endif +int tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file, + const char *priv_key_file_inline ); #ifdef MANAGMENT_EXTERNAL_KEY @@ -234,9 +223,9 @@ int tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file * successful. */ int tls_ctx_use_external_private_key (struct tls_root_ctx *ctx, openvpn_x509_cert_t *cert); - #endif + /** * Load certificate authority certificates from the given file or path. * @@ -249,10 +238,7 @@ int tls_ctx_use_external_private_key (struct tls_root_ctx *ctx, openvpn_x509_cer * @param ca_path The path to load the CAs from */ void tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, -#if ENABLE_INLINE_FILES - const char *ca_file_inline, -#endif - const char *ca_path, bool tls_server + const char *ca_file_inline, const char *ca_path, bool tls_server ); /** @@ -266,10 +252,8 @@ void tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, * "[[INLINE]]" in the case of inline files. * @param extra_certs_file_inline A string containing the certs */ -void tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file -#if ENABLE_INLINE_FILES - , const char *extra_certs_file_inline -#endif +void tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file, + const char *extra_certs_file_inline ); #ifdef ENABLE_CRYPTO_POLARSSL diff --git a/openvpn/src/openvpn/ssl_openssl.c b/openvpn/src/openvpn/ssl_openssl.c index 8f353253..a727b605 100644 --- a/openvpn/src/openvpn/ssl_openssl.c +++ b/openvpn/src/openvpn/ssl_openssl.c @@ -209,10 +209,8 @@ tls_ctx_restrict_ciphers(struct tls_root_ctx *ctx, const char *ciphers) } void -tls_ctx_load_dh_params (struct tls_root_ctx *ctx, const char *dh_file -#if ENABLE_INLINE_FILES - , const char *dh_file_inline -#endif /* ENABLE_INLINE_FILES */ +tls_ctx_load_dh_params (struct tls_root_ctx *ctx, const char *dh_file, + const char *dh_file_inline ) { DH *dh; @@ -220,14 +218,12 @@ tls_ctx_load_dh_params (struct tls_root_ctx *ctx, const char *dh_file ASSERT(NULL != ctx); -#if ENABLE_INLINE_FILES if (!strcmp (dh_file, INLINE_FILE_TAG) && dh_file_inline) { if (!(bio = BIO_new_mem_buf ((char *)dh_file_inline, -1))) msg (M_SSLERR, "Cannot open memory BIO for inline DH parameters"); } else -#endif /* ENABLE_INLINE_FILES */ { /* Get Diffie Hellman Parameters */ if (!(bio = BIO_new_file (dh_file, "r"))) @@ -250,9 +246,7 @@ tls_ctx_load_dh_params (struct tls_root_ctx *ctx, const char *dh_file int tls_ctx_load_pkcs12(struct tls_root_ctx *ctx, const char *pkcs12_file, -#if ENABLE_INLINE_FILES const char *pkcs12_file_inline, -#endif /* ENABLE_INLINE_FILES */ bool load_ca_file ) { @@ -266,7 +260,6 @@ tls_ctx_load_pkcs12(struct tls_root_ctx *ctx, const char *pkcs12_file, ASSERT(NULL != ctx); -#if ENABLE_INLINE_FILES if (!strcmp (pkcs12_file, INLINE_FILE_TAG) && pkcs12_file_inline) { BIO *b64 = BIO_new(BIO_f_base64()); @@ -281,7 +274,6 @@ tls_ctx_load_pkcs12(struct tls_root_ctx *ctx, const char *pkcs12_file, BIO_free(bio); } else -#endif { /* Load the PKCS #12 file */ if (!(fp = platform_fopen(pkcs12_file, "rb"))) @@ -371,10 +363,7 @@ tls_ctx_add_extra_certs (struct tls_root_ctx *ctx, BIO *bio) void tls_ctx_load_cert_file (struct tls_root_ctx *ctx, const char *cert_file, -#if ENABLE_INLINE_FILES - const char *cert_file_inline, -#endif - X509 **x509 + const char *cert_file_inline, X509 **x509 ) { BIO *in = NULL; @@ -386,13 +375,11 @@ tls_ctx_load_cert_file (struct tls_root_ctx *ctx, const char *cert_file, if (NULL != x509) ASSERT (NULL == *x509); -#if ENABLE_INLINE_FILES inline_file = (strcmp (cert_file, INLINE_FILE_TAG) == 0); if (inline_file && cert_file_inline) in = BIO_new_mem_buf ((char *)cert_file_inline, -1); else -#endif /* ENABLE_INLINE_FILES */ in = BIO_new_file (cert_file, "r"); if (in == NULL) @@ -437,10 +424,8 @@ tls_ctx_free_cert_file (X509 *x509) } int -tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file -#if ENABLE_INLINE_FILES - , const char *priv_key_file_inline -#endif +tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file, + const char *priv_key_file_inline ) { int status; @@ -453,11 +438,9 @@ tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file ssl_ctx = ctx->ctx; -#if ENABLE_INLINE_FILES if (!strcmp (priv_key_file, INLINE_FILE_TAG) && priv_key_file_inline) in = BIO_new_mem_buf ((char *)priv_key_file_inline, -1); else -#endif /* ENABLE_INLINE_FILES */ in = BIO_new_file (priv_key_file, "r"); if (!in) @@ -639,9 +622,7 @@ sk_x509_name_cmp(const X509_NAME * const *a, const X509_NAME * const *b) void tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, -#if ENABLE_INLINE_FILES const char *ca_file_inline, -#endif const char *ca_path, bool tls_server ) { @@ -662,11 +643,9 @@ tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, /* Try to add certificates and CRLs from ca_file */ if (ca_file) { -#if ENABLE_INLINE_FILES if (!strcmp (ca_file, INLINE_FILE_TAG) && ca_file_inline) in = BIO_new_mem_buf ((char *)ca_file_inline, -1); else -#endif in = BIO_new_file (ca_file, "r"); if (in) @@ -739,18 +718,14 @@ tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, } void -tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file -#if ENABLE_INLINE_FILES - , const char *extra_certs_file_inline -#endif +tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file, + const char *extra_certs_file_inline ) { BIO *in; -#if ENABLE_INLINE_FILES if (!strcmp (extra_certs_file, INLINE_FILE_TAG) && extra_certs_file_inline) in = BIO_new_mem_buf ((char *)extra_certs_file_inline, -1); else -#endif in = BIO_new_file (extra_certs_file, "r"); if (in == NULL) diff --git a/openvpn/src/openvpn/ssl_polarssl.c b/openvpn/src/openvpn/ssl_polarssl.c index fc8fa6e9..6995958b 100644 --- a/openvpn/src/openvpn/ssl_polarssl.c +++ b/openvpn/src/openvpn/ssl_polarssl.c @@ -195,20 +195,16 @@ tls_ctx_restrict_ciphers(struct tls_root_ctx *ctx, const char *ciphers) } void -tls_ctx_load_dh_params (struct tls_root_ctx *ctx, const char *dh_file -#if ENABLE_INLINE_FILES - , const char *dh_file_inline -#endif /* ENABLE_INLINE_FILES */ +tls_ctx_load_dh_params (struct tls_root_ctx *ctx, const char *dh_file, + const char *dh_file_inline ) { -#if ENABLE_INLINE_FILES if (!strcmp (dh_file, INLINE_FILE_TAG) && dh_file_inline) { if (0 != x509parse_dhm(ctx->dhm_ctx, dh_file_inline, strlen(dh_file_inline))) msg (M_FATAL, "Cannot read inline DH parameters"); } else -#endif /* ENABLE_INLINE_FILES */ { if (0 != x509parse_dhmfile(ctx->dhm_ctx, dh_file)) msg (M_FATAL, "Cannot read DH parameters from file %s", dh_file); @@ -220,9 +216,7 @@ else int tls_ctx_load_pkcs12(struct tls_root_ctx *ctx, const char *pkcs12_file, -#if ENABLE_INLINE_FILES const char *pkcs12_file_inline, -#endif /* ENABLE_INLINE_FILES */ bool load_ca_file ) { @@ -240,9 +234,7 @@ tls_ctx_load_cryptoapi(struct tls_root_ctx *ctx, const char *cryptoapi_cert) void tls_ctx_load_cert_file (struct tls_root_ctx *ctx, const char *cert_file, -#if ENABLE_INLINE_FILES const char *cert_file_inline, -#endif openvpn_x509_cert_t **x509 ) { @@ -250,7 +242,6 @@ tls_ctx_load_cert_file (struct tls_root_ctx *ctx, const char *cert_file, if (NULL != x509) ASSERT(NULL == *x509); -#if ENABLE_INLINE_FILES if (!strcmp (cert_file, INLINE_FILE_TAG) && cert_file_inline) { if (0 != x509parse_crt(ctx->crt_chain, cert_file_inline, @@ -258,7 +249,6 @@ tls_ctx_load_cert_file (struct tls_root_ctx *ctx, const char *cert_file, msg (M_FATAL, "Cannot load inline certificate file"); } else -#endif /* ENABLE_INLINE_FILES */ { if (0 != x509parse_crtfile(ctx->crt_chain, cert_file)) msg (M_FATAL, "Cannot load certificate file %s", cert_file); @@ -276,16 +266,13 @@ tls_ctx_free_cert_file (openvpn_x509_cert_t *x509) } int -tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file -#if ENABLE_INLINE_FILES - , const char *priv_key_file_inline -#endif /* ENABLE_INLINE_FILES */ +tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file, + const char *priv_key_file_inline ) { int status; ASSERT(NULL != ctx); -#if ENABLE_INLINE_FILES if (!strcmp (priv_key_file, INLINE_FILE_TAG) && priv_key_file_inline) { status = x509parse_key(ctx->priv_key, @@ -301,7 +288,6 @@ tls_ctx_load_priv_file (struct tls_root_ctx *ctx, const char *priv_key_file } } else -#endif /* ENABLE_INLINE_FILES */ { status = x509parse_keyfile(ctx->priv_key, priv_key_file, NULL); if (POLARSSL_ERR_PEM_PASSWORD_REQUIRED == status) @@ -343,23 +329,19 @@ tls_ctx_use_external_private_key (struct tls_root_ctx *ctx, openvpn_x509_cert_t #endif void tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, -#if ENABLE_INLINE_FILES const char *ca_file_inline, -#endif const char *ca_path, bool tls_server ) { if (ca_path) msg(M_FATAL, "ERROR: PolarSSL cannot handle the capath directive"); -#if ENABLE_INLINE_FILES if (ca_file && !strcmp (ca_file, INLINE_FILE_TAG) && ca_file_inline) { if (0 != x509parse_crt(ctx->ca_chain, ca_file_inline, strlen(ca_file_inline))); msg (M_FATAL, "Cannot load inline CA certificates"); } else -#endif { /* Load CA file for verifying peer supplied certificate */ if (0 != x509parse_crtfile(ctx->ca_chain, ca_file)) @@ -368,15 +350,12 @@ void tls_ctx_load_ca (struct tls_root_ctx *ctx, const char *ca_file, } void -tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file -#if ENABLE_INLINE_FILES - , const char *extra_certs_file_inline -#endif +tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file, + const char *extra_certs_file_inline ) { ASSERT(NULL != ctx); -#if ENABLE_INLINE_FILES if (!strcmp (extra_certs_file, INLINE_FILE_TAG) && extra_certs_file_inline) { if (0 != x509parse_crt(ctx->crt_chain, extra_certs_file_inline, @@ -384,7 +363,6 @@ tls_ctx_load_extra_certs (struct tls_root_ctx *ctx, const char *extra_certs_file msg (M_FATAL, "Cannot load inline extra-certs file"); } else -#endif /* ENABLE_INLINE_FILES */ { if (0 != x509parse_crtfile(ctx->crt_chain, extra_certs_file)) msg (M_FATAL, "Cannot load extra-certs file: %s", extra_certs_file); diff --git a/openvpn/src/openvpn/ssl_polarssl.h b/openvpn/src/openvpn/ssl_polarssl.h index 2b02a6fd..456573f5 100644 --- a/openvpn/src/openvpn/ssl_polarssl.h +++ b/openvpn/src/openvpn/ssl_polarssl.h @@ -31,7 +31,6 @@ #define SSL_POLARSSL_H_ #include -#include "config.h" #if defined(ENABLE_PKCS11) #include diff --git a/openvpn/src/openvpn/syshead.h b/openvpn/src/openvpn/syshead.h index ed00e821..163d2bb2 100644 --- a/openvpn/src/openvpn/syshead.h +++ b/openvpn/src/openvpn/syshead.h @@ -506,7 +506,6 @@ socket_defined (const socket_descriptor_t sd) #if P2MP && !defined(ENABLE_CLIENT_ONLY) #define P2MP_SERVER 1 -#define ENABLE_TMPDIR 1 #else #define P2MP_SERVER 0 #endif @@ -651,34 +650,12 @@ socket_defined (const socket_descriptor_t sd) #endif /* - * Should we allow ca/cert/key files to be - * included inline, in the configuration file? + * Should we include http proxy override functionality */ -#define ENABLE_INLINE_FILES 1 - -/* - * Support "connection" directive - */ -#if ENABLE_INLINE_FILES -#define ENABLE_CONNECTION 1 -#endif - -/* - * Should we include http proxy fallback functionality - */ -#if defined(ENABLE_CONNECTION) && defined(ENABLE_MANAGEMENT) && defined(ENABLE_HTTP_PROXY) -#define HTTP_PROXY_FALLBACK 1 -#else -#define HTTP_PROXY_FALLBACK 0 -#endif - -/* - * Should we include --management-query-remote functionality - */ -#if defined(ENABLE_CONNECTION) && defined(ENABLE_MANAGEMENT) -#define MANAGEMENT_QUERY_REMOTE 1 +#if defined(ENABLE_MANAGEMENT) && defined(ENABLE_HTTP_PROXY) +#define HTTP_PROXY_OVERRIDE 1 #else -#define MANAGEMENT_QUERY_REMOTE 0 +#define HTTP_PROXY_OVERRIDE 0 #endif /* diff --git a/openvpn/src/openvpn/tun.c b/openvpn/src/openvpn/tun.c index 8057c16e..81979476 100644 --- a/openvpn/src/openvpn/tun.c +++ b/openvpn/src/openvpn/tun.c @@ -601,6 +601,8 @@ void add_route_connected_v6_net(struct tuntap * tt, r6.network = tt->local_ipv6; r6.netbits = tt->netbits_ipv6; r6.gateway = tt->local_ipv6; + r6.metric = 0; /* connected route */ + r6.metric_defined = true; add_route_ipv6 (&r6, tt, 0, es); } @@ -613,6 +615,8 @@ void delete_route_connected_v6_net(struct tuntap * tt, r6.network = tt->local_ipv6; r6.netbits = tt->netbits_ipv6; r6.gateway = tt->local_ipv6; + r6.metric = 0; /* connected route */ + r6.metric_defined = true; delete_route_ipv6 (&r6, tt, 0, es); } #endif @@ -1797,6 +1801,12 @@ open_tun (const char *dev, const char *dev_type, const char *dev_node, struct tu msg (M_FATAL, "I don't recognize device %s as a tun or tap device", dev); } + + if ((tt->ip_fd = open (ip_node, O_RDWR, 0)) < 0) + msg (M_ERR, "Can't open %s", ip_node); + + if ((tt->fd = open (dev_node, O_RDWR, 0)) < 0) + msg (M_ERR, "Can't open %s", dev_node); /* get unit number */ if (*dev) @@ -1807,19 +1817,37 @@ open_tun (const char *dev, const char *dev_type, const char *dev_node, struct tu ppa = atoi (ptr); } - if ((tt->ip_fd = open (ip_node, O_RDWR, 0)) < 0) - msg (M_ERR, "Can't open %s", ip_node); - - if ((tt->fd = open (dev_node, O_RDWR, 0)) < 0) - msg (M_ERR, "Can't open %s", dev_node); - /* Assign a new PPA and get its unit number. */ strioc_ppa.ic_cmd = TUNNEWPPA; strioc_ppa.ic_timout = 0; strioc_ppa.ic_len = sizeof(ppa); strioc_ppa.ic_dp = (char *)&ppa; - if ((ppa = ioctl (tt->fd, I_STR, &strioc_ppa)) < 0) - msg (M_ERR, "Can't assign new interface"); + + if ( *ptr == '\0' ) /* no number given, try dynamic */ + { + bool found_one = false; + while( ! found_one && ppa < 64 ) + { + int new_ppa = ioctl (tt->fd, I_STR, &strioc_ppa); + if ( new_ppa >= 0 ) + { + msg( M_INFO, "open_tun: got dynamic interface '%s%d'", dev_tuntap_type, new_ppa ); + ppa = new_ppa; + found_one = true; + break; + } + if ( errno != EEXIST ) + msg (M_ERR, "open_tun: unexpected error trying to find free %s interface", dev_tuntap_type ); + ppa++; + } + if ( !found_one ) + msg (M_ERR, "open_tun: could not find free %s interface, give up.", dev_tuntap_type ); + } + else /* try this particular one */ + { + if ((ppa = ioctl (tt->fd, I_STR, &strioc_ppa)) < 0) + msg (M_ERR, "Can't assign PPA for new interface (%s%d)", dev_tuntap_type, ppa ); + } if ((if_fd = open (dev_node, O_RDWR, 0)) < 0) msg (M_ERR, "Can't open %s (2)", dev_node); @@ -2524,7 +2552,7 @@ read_tun (struct tuntap* tt, uint8_t *buf, int len) void open_tun (const char *dev, const char *dev_type, const char *dev_node, struct tuntap *tt) { - open_tun_generic (dev, dev_type, dev_node, false, true, tt); + open_tun_generic (dev, dev_type, dev_node, true, true, tt); } void diff --git a/openvpn/src/openvpn/win32.c b/openvpn/src/openvpn/win32.c index e8e69dcd..d00088eb 100644 --- a/openvpn/src/openvpn/win32.c +++ b/openvpn/src/openvpn/win32.c @@ -257,7 +257,7 @@ init_net_event_win32 (struct rw_handle *event, long network_events, socket_descr /* setup network events to change read event state */ if (WSAEventSelect (sd, event->read, network_events) != 0) - msg (M_FATAL | M_ERRNO_SOCK, "Error: init_net_event_win32: WSAEventSelect call failed"); + msg (M_FATAL | M_ERRNO, "Error: init_net_event_win32: WSAEventSelect call failed"); } long @@ -266,7 +266,7 @@ reset_net_event_win32 (struct rw_handle *event, socket_descriptor_t sd) WSANETWORKEVENTS wne; if (WSAEnumNetworkEvents (sd, event->read, &wne) != 0) { - msg (M_FATAL | M_ERRNO_SOCK, "Error: reset_net_event_win32: WSAEnumNetworkEvents call failed"); + msg (M_FATAL | M_ERRNO, "Error: reset_net_event_win32: WSAEnumNetworkEvents call failed"); return 0; /* NOTREACHED */ } else @@ -281,7 +281,7 @@ close_net_event_win32 (struct rw_handle *event, socket_descriptor_t sd, unsigned if (socket_defined (sd)) { if (WSAEventSelect (sd, event->read, 0) != 0) - msg (M_WARN | M_ERRNO_SOCK, "Warning: close_net_event_win32: WSAEventSelect call failed"); + msg (M_WARN | M_ERRNO, "Warning: close_net_event_win32: WSAEventSelect call failed"); } if (!ResetEvent (event->read)) msg (M_WARN | M_ERRNO, "Warning: ResetEvent (read) failed in close_net_event_win32"); diff --git a/openvpn/src/plugins/Makefile.am b/openvpn/src/plugins/Makefile.am new file mode 100644 index 00000000..17b72b94 --- /dev/null +++ b/openvpn/src/plugins/Makefile.am @@ -0,0 +1,15 @@ +# +# OpenVPN -- An application to securely tunnel IP networks +# over a single UDP port, with support for SSL/TLS-based +# session authentication and key exchange, +# packet encryption, packet authentication, and +# packet compression. +# +# Copyright (C) 2002-2010 OpenVPN Technologies, Inc. +# Copyright (C) 2006-2012 Alon Bar-Lev +# + +MAINTAINERCLEANFILES = \ + $(srcdir)/Makefile.in + +SUBDIRS = auth-pam down-root diff --git a/openvpn/src/plugins/README b/openvpn/src/plugins/README deleted file mode 100644 index 6e490c5a..00000000 --- a/openvpn/src/plugins/README +++ /dev/null @@ -1,47 +0,0 @@ -OpenVPN Plugins ---------------- - -Starting with OpenVPN 2.0-beta17, compiled plugin modules are -supported on any *nix OS which includes libdl or on Windows. -One or more modules may be loaded into OpenVPN using -the --plugin directive, and each plugin module is capable of -intercepting any of the script callbacks which OpenVPN supports: - -(1) up -(2) down -(3) route-up -(4) ipchange -(5) tls-verify -(6) auth-user-pass-verify -(7) client-connect -(8) client-disconnect -(9) learn-address - -See the openvpn-plugin.h file in the top-level directory of the -OpenVPN source distribution for more detailed information -on the plugin interface. - -Included Plugins ----------------- - -auth-pam -- Authenticate using PAM and a split privilege - execution model which functions even if - root privileges or the execution environment - have been altered with --user/--group/--chroot. - Tested on Linux only. - -down-root -- Enable the running of down scripts with root privileges - even if --user/--group/--chroot have been used - to drop root privileges or change the execution - environment. Not applicable on Windows. - -examples -- A simple example that demonstrates a portable - plugin, i.e. one which can be built for *nix - or Windows from the same source. - -Building Plugins ----------------- - -cd to the top-level directory of a plugin, and use the -"make" command to build it. The examples plugin is -built using a build script, not a makefile. diff --git a/openvpn/src/plugins/auth-pam/Makefile b/openvpn/src/plugins/auth-pam/Makefile deleted file mode 100755 index c0b9c79e..00000000 --- a/openvpn/src/plugins/auth-pam/Makefile +++ /dev/null @@ -1,32 +0,0 @@ -# -# Build the OpenVPN auth-pam plugin module. -# - -# If PAM modules are not linked against libpam.so, set DLOPEN_PAM to 1. This -# must be done on SUSE 9.1, at least. -DLOPEN_PAM=0 - -ifeq ($(DLOPEN_PAM),1) - LIBPAM=-ldl -else - LIBPAM=-lpam -endif - -# This directory is where we will look for openvpn-plugin.h -CPPFLAGS=-I../../../include - -CC=gcc -CFLAGS=-O2 -Wall -DEFS = -DDLOPEN_PAM=$(DLOPEN_PAM) - -openvpn-auth-pam.so : auth-pam.o pamdl.o - $(CC) $(CFLAGS) -fPIC -shared $(LDFLAGS) -Wl,-soname,openvpn-auth-pam.so -o openvpn-auth-pam.so auth-pam.o pamdl.o -lc $(LIBPAM) - -auth-pam.o : auth-pam.c pamdl.h - $(CC) $(CPPFLAGS) $(CFLAGS) $(DEFS) -fPIC -c auth-pam.c - -pamdl.o : pamdl.c pamdl.h - $(CC) $(CPPFLAGS) $(CFLAGS) $(DEFS) -fPIC -c pamdl.c - -clean : - -rm -f *.o *.so diff --git a/openvpn/src/plugins/auth-pam/Makefile.am b/openvpn/src/plugins/auth-pam/Makefile.am new file mode 100644 index 00000000..701a7497 --- /dev/null +++ b/openvpn/src/plugins/auth-pam/Makefile.am @@ -0,0 +1,27 @@ +# +# OpenVPN (TM) PAM Auth Plugin -- OpenVPN Plugin +# +# Copyright (C) 2012 Alon Bar-Lev +# + +MAINTAINERCLEANFILES = \ + $(srcdir)/Makefile.in + +AM_CFLAGS = \ + -I$(top_srcdir)/include + $(PLUGIN_AUTH_PAM_CFLAGS) + +if ENABLE_PLUGIN_AUTH_PAM +plugin_LTLIBRARIES = openvpn-plugin-auth-pam.la +dist_doc_DATA = README.auth-pam +endif + +openvpn_plugin_auth_pam_la_SOURCES = \ + auth-pam.c \ + pamdl.c pamdl.h \ + auth-pam.exports +openvpn_plugin_auth_pam_la_LIBADD = \ + $(PLUGIN_AUTH_PAM_LIBS) +openvpn_plugin_auth_pam_la_LDFLAGS = $(AM_LDFLAGS) \ + -export-symbols "$(srcdir)/auth-pam.exports" \ + -module -shared -avoid-version -no-undefined diff --git a/openvpn/src/plugins/auth-pam/README b/openvpn/src/plugins/auth-pam/README deleted file mode 100644 index e1236902..00000000 --- a/openvpn/src/plugins/auth-pam/README +++ /dev/null @@ -1,74 +0,0 @@ -openvpn-auth-pam - -SYNOPSIS - -The openvpn-auth-pam module implements username/password -authentication via PAM, and essentially allows any authentication -method supported by PAM (such as LDAP, RADIUS, or Linux Shadow -passwords) to be used with OpenVPN. While PAM supports -username/password authentication, this can be combined with X509 -certificates to provide two indepedent levels of authentication. - -This module uses a split privilege execution model which will -function even if you drop openvpn daemon privileges using the user, -group, or chroot directives. - -BUILD - -To build openvpn-auth-pam, you will need to have the pam-devel -package installed. - -Build with the "make" command. The module will be named -openvpn-auth-pam.so - -USAGE - -To use this plugin module, add to your OpenVPN config file: - - plugin openvpn-auth-pam.so service-type - -The required service-type parameter corresponds to -the PAM service definition file usually found -in /etc/pam.d. - -This plugin also supports the usage of a list of name/value -pairs to answer PAM module queries. - -For example: - - plugin openvpn-auth-pam.so "login login USERNAME password PASSWORD" - -tells auth-pam to (a) use the "login" PAM module, (b) answer a -"login" query with the username given by the OpenVPN client, and -(c) answer a "password" query with the password given by the -OpenVPN client. This provides flexibility in dealing with the different -types of query strings which different PAM modules might generate. -For example, suppose you were using a PAM module called -"test" which queried for "name" rather than "login": - - plugin openvpn-auth-pam.so "test name USERNAME password PASSWORD" - -While "USERNAME" "COMMONNAME" and "PASSWORD" are special strings which substitute -to client-supplied values, it is also possible to name literal values -to use as PAM module query responses. For example, suppose that the -login module queried for a third parameter, "domain" which -is to be answered with the constant value "mydomain.com": - - plugin openvpn-auth-pam.so "login login USERNAME password PASSWORD domain mydomain.com" - -The following OpenVPN directives can also influence -the operation of this plugin: - - client-cert-not-required - username-as-common-name - -Run OpenVPN with --verb 7 or higher to get debugging output from -this plugin, including the list of queries presented by the -underlying PAM module. This is a useful debugging tool to figure -out which queries a given PAM module is making, so that you can -craft the appropriate plugin directive to answer it. - -CAVEATS - -This module will only work on *nix systems which support PAM, -not Windows. diff --git a/openvpn/src/plugins/auth-pam/README.auth-pam b/openvpn/src/plugins/auth-pam/README.auth-pam new file mode 100644 index 00000000..e1236902 --- /dev/null +++ b/openvpn/src/plugins/auth-pam/README.auth-pam @@ -0,0 +1,74 @@ +openvpn-auth-pam + +SYNOPSIS + +The openvpn-auth-pam module implements username/password +authentication via PAM, and essentially allows any authentication +method supported by PAM (such as LDAP, RADIUS, or Linux Shadow +passwords) to be used with OpenVPN. While PAM supports +username/password authentication, this can be combined with X509 +certificates to provide two indepedent levels of authentication. + +This module uses a split privilege execution model which will +function even if you drop openvpn daemon privileges using the user, +group, or chroot directives. + +BUILD + +To build openvpn-auth-pam, you will need to have the pam-devel +package installed. + +Build with the "make" command. The module will be named +openvpn-auth-pam.so + +USAGE + +To use this plugin module, add to your OpenVPN config file: + + plugin openvpn-auth-pam.so service-type + +The required service-type parameter corresponds to +the PAM service definition file usually found +in /etc/pam.d. + +This plugin also supports the usage of a list of name/value +pairs to answer PAM module queries. + +For example: + + plugin openvpn-auth-pam.so "login login USERNAME password PASSWORD" + +tells auth-pam to (a) use the "login" PAM module, (b) answer a +"login" query with the username given by the OpenVPN client, and +(c) answer a "password" query with the password given by the +OpenVPN client. This provides flexibility in dealing with the different +types of query strings which different PAM modules might generate. +For example, suppose you were using a PAM module called +"test" which queried for "name" rather than "login": + + plugin openvpn-auth-pam.so "test name USERNAME password PASSWORD" + +While "USERNAME" "COMMONNAME" and "PASSWORD" are special strings which substitute +to client-supplied values, it is also possible to name literal values +to use as PAM module query responses. For example, suppose that the +login module queried for a third parameter, "domain" which +is to be answered with the constant value "mydomain.com": + + plugin openvpn-auth-pam.so "login login USERNAME password PASSWORD domain mydomain.com" + +The following OpenVPN directives can also influence +the operation of this plugin: + + client-cert-not-required + username-as-common-name + +Run OpenVPN with --verb 7 or higher to get debugging output from +this plugin, including the list of queries presented by the +underlying PAM module. This is a useful debugging tool to figure +out which queries a given PAM module is making, so that you can +craft the appropriate plugin directive to answer it. + +CAVEATS + +This module will only work on *nix systems which support PAM, +not Windows. diff --git a/openvpn/src/plugins/auth-pam/auth-pam.c b/openvpn/src/plugins/auth-pam/auth-pam.c index e52f6322..bd717927 100644 --- a/openvpn/src/plugins/auth-pam/auth-pam.c +++ b/openvpn/src/plugins/auth-pam/auth-pam.c @@ -26,12 +26,14 @@ * OpenVPN plugin module to do PAM authentication using a split * privilege model. */ +#ifdef HAVE_CONFIG_H +#include +#endif -#if DLOPEN_PAM -#include -#include "pamdl.h" -#else #include + +#ifdef USE_PAM_DLOPEN +#include "pamdl.h" #endif #include @@ -46,7 +48,7 @@ #include #include -#include "openvpn-plugin.h" +#include #define DEBUG(verb) ((verb) >= 4) @@ -693,7 +695,7 @@ pam_server (int fd, const char *service, int verb, const struct name_value_list { struct user_pass up; int command; -#if DLOPEN_PAM +#ifdef USE_PAM_DLOPEN static const char pam_so[] = "libpam.so"; #endif @@ -703,7 +705,7 @@ pam_server (int fd, const char *service, int verb, const struct name_value_list if (DEBUG (verb)) fprintf (stderr, "AUTH-PAM: BACKGROUND: INIT service='%s'\n", service); -#if DLOPEN_PAM +#ifdef USE_PAM_DLOPEN /* * Load PAM shared object */ @@ -794,7 +796,7 @@ pam_server (int fd, const char *service, int verb, const struct name_value_list } done: -#if DLOPEN_PAM +#ifdef USE_PAM_DLOPEN dlclose_pam (); #endif if (DEBUG (verb)) diff --git a/openvpn/src/plugins/auth-pam/auth-pam.exports b/openvpn/src/plugins/auth-pam/auth-pam.exports new file mode 100644 index 00000000..b07937cc --- /dev/null +++ b/openvpn/src/plugins/auth-pam/auth-pam.exports @@ -0,0 +1,4 @@ +openvpn_plugin_open_v1 +openvpn_plugin_func_v1 +openvpn_plugin_close_v1 +openvpn_plugin_abort_v1 diff --git a/openvpn/src/plugins/auth-pam/pamdl.c b/openvpn/src/plugins/auth-pam/pamdl.c index 8636a8e4..26e98215 100644 --- a/openvpn/src/plugins/auth-pam/pamdl.c +++ b/openvpn/src/plugins/auth-pam/pamdl.c @@ -1,4 +1,8 @@ -#if DLOPEN_PAM +#ifdef HAVE_CONFIG_H +#include +#endif + +#ifdef USE_PAM_DLOPEN /* * If you want to dynamically load libpam using dlopen() or something, * then dlopen( ' this shared object ' ); It takes care of exporting @@ -73,7 +77,7 @@ int pam_set_item(pam_handle_t *pamh, int item_type, const void *item) return real_pam_set_item(pamh, item_type, item); } -int pam_get_item(pam_handle_t *pamh, int item_type, const void **item) +int pam_get_item(const pam_handle_t *pamh, int item_type, const void **item) { int (*real_pam_get_item)(const pam_handle_t *, int, const void **); RESOLVE_PAM_FUNCTION(pam_get_item, int, diff --git a/openvpn/src/plugins/auth-pam/pamdl.h b/openvpn/src/plugins/auth-pam/pamdl.h index b10b035a..12ba0684 100644 --- a/openvpn/src/plugins/auth-pam/pamdl.h +++ b/openvpn/src/plugins/auth-pam/pamdl.h @@ -1,6 +1,4 @@ -#if DLOPEN_PAM -#include - +#ifdef USE_PAM_DLOPEN /* Dynamically load and unload the PAM library */ int dlopen_pam (const char *so); void dlclose_pam (void); diff --git a/openvpn/src/plugins/defer/README b/openvpn/src/plugins/defer/README deleted file mode 100644 index d8990f8b..00000000 --- a/openvpn/src/plugins/defer/README +++ /dev/null @@ -1,16 +0,0 @@ -OpenVPN plugin examples. - -Examples provided: - -simple.c -- using the --auth-user-pass-verify callback, - test deferred authentication. - -To build: - - ./build simple (Linux/BSD/etc.) - ./winbuild simple (MinGW on Windows) - -To use in OpenVPN, add to config file: - - plugin simple.so (Linux/BSD/etc.) - plugin simple.dll (MinGW on Windows) diff --git a/openvpn/src/plugins/defer/build b/openvpn/src/plugins/defer/build deleted file mode 100755 index 0612c080..00000000 --- a/openvpn/src/plugins/defer/build +++ /dev/null @@ -1,15 +0,0 @@ -#!/bin/sh - -# -# Build an OpenVPN plugin module on *nix. The argument should -# be the base name of the C source file (without the .c). -# - -# This directory is where we will look for openvpn-plugin.h -CPPFLAGS="${CPPFLAGS:--I../../../include}" - -CC="${CC:-gcc}" -CFLAGS="${CFLAGS:--O2 -Wall -g}" - -$CC $CPPFLAGS $CFLAGS -fPIC -c $1.c && \ -$CC $CFLAGS -fPIC -shared ${LDFLAS} -Wl,-soname,$1.so -o $1.so $1.o -lc diff --git a/openvpn/src/plugins/defer/simple.c b/openvpn/src/plugins/defer/simple.c deleted file mode 100644 index 65398657..00000000 --- a/openvpn/src/plugins/defer/simple.c +++ /dev/null @@ -1,305 +0,0 @@ -/* - * OpenVPN -- An application to securely tunnel IP networks - * over a single TCP/UDP port, with support for SSL/TLS-based - * session authentication and key exchange, - * packet encryption, packet authentication, and - * packet compression. - * - * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 - * as published by the Free Software Foundation. - * - * 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 (see the file COPYING included with this - * distribution); if not, write to the Free Software Foundation, Inc., - * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -/* - * This file implements a simple OpenVPN plugin module which - * will test deferred authentication and packet filtering. - * - * Will run on Windows or *nix. - * - * Sample usage: - * - * setenv test_deferred_auth 20 - * setenv test_packet_filter 10 - * plugin plugin/defer/simple.so - * - * This will enable deferred authentication to occur 20 - * seconds after the normal TLS authentication process, - * and will cause a packet filter file to be generated 10 - * seconds after the initial TLS negotiation, using - * {common-name}.pf as the source. - * - * Sample packet filter configuration: - * - * [CLIENTS DROP] - * +otherclient - * [SUBNETS DROP] - * +10.0.0.0/8 - * -10.10.0.8 - * [END] - * - * See the README file for build instructions. - */ - -#include -#include -#include - -#include "openvpn-plugin.h" - -/* bool definitions */ -#define bool int -#define true 1 -#define false 0 - -/* - * Our context, where we keep our state. - */ - -struct plugin_context { - int test_deferred_auth; - int test_packet_filter; -}; - -struct plugin_per_client_context { - int n_calls; - bool generated_pf_file; -}; - -/* - * Given an environmental variable name, search - * the envp array for its value, returning it - * if found or NULL otherwise. - */ -static const char * -get_env (const char *name, const char *envp[]) -{ - if (envp) - { - int i; - const int namelen = strlen (name); - for (i = 0; envp[i]; ++i) - { - if (!strncmp (envp[i], name, namelen)) - { - const char *cp = envp[i] + namelen; - if (*cp == '=') - return cp + 1; - } - } - } - return NULL; -} - -/* used for safe printf of possible NULL strings */ -static const char * -np (const char *str) -{ - if (str) - return str; - else - return "[NULL]"; -} - -static int -atoi_null0 (const char *str) -{ - if (str) - return atoi (str); - else - return 0; -} - -OPENVPN_EXPORT openvpn_plugin_handle_t -openvpn_plugin_open_v1 (unsigned int *type_mask, const char *argv[], const char *envp[]) -{ - struct plugin_context *context; - - printf ("FUNC: openvpn_plugin_open_v1\n"); - - /* - * Allocate our context - */ - context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); - - context->test_deferred_auth = atoi_null0 (get_env ("test_deferred_auth", envp)); - printf ("TEST_DEFERRED_AUTH %d\n", context->test_deferred_auth); - - context->test_packet_filter = atoi_null0 (get_env ("test_packet_filter", envp)); - printf ("TEST_PACKET_FILTER %d\n", context->test_packet_filter); - - /* - * Which callbacks to intercept. - */ - *type_mask = - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_UP) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_DOWN) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ROUTE_UP) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_IPCHANGE) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_VERIFY) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_CONNECT_V2) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_DISCONNECT) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_LEARN_ADDRESS) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_FINAL) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ENABLE_PF); - - return (openvpn_plugin_handle_t) context; -} - -static int -auth_user_pass_verify (struct plugin_context *context, struct plugin_per_client_context *pcc, const char *argv[], const char *envp[]) -{ - if (context->test_deferred_auth) - { - /* get username/password from envp string array */ - const char *username = get_env ("username", envp); - const char *password = get_env ("password", envp); - - /* get auth_control_file filename from envp string array*/ - const char *auth_control_file = get_env ("auth_control_file", envp); - - printf ("DEFER u='%s' p='%s' acf='%s'\n", - np(username), - np(password), - np(auth_control_file)); - - /* Authenticate asynchronously in n seconds */ - if (auth_control_file) - { - char buf[256]; - int auth = 2; - sscanf (username, "%d", &auth); - snprintf (buf, sizeof(buf), "( sleep %d ; echo AUTH %s %d ; echo %d >%s ) &", - context->test_deferred_auth, - auth_control_file, - auth, - pcc->n_calls < auth, - auth_control_file); - printf ("%s\n", buf); - system (buf); - pcc->n_calls++; - return OPENVPN_PLUGIN_FUNC_DEFERRED; - } - else - return OPENVPN_PLUGIN_FUNC_ERROR; - } - else - return OPENVPN_PLUGIN_FUNC_SUCCESS; -} - -static int -tls_final (struct plugin_context *context, struct plugin_per_client_context *pcc, const char *argv[], const char *envp[]) -{ - if (context->test_packet_filter) - { - if (!pcc->generated_pf_file) - { - const char *pff = get_env ("pf_file", envp); - const char *cn = get_env ("username", envp); - if (pff && cn) - { - char buf[256]; - snprintf (buf, sizeof(buf), "( sleep %d ; echo PF %s/%s ; cp \"%s.pf\" \"%s\" ) &", - context->test_packet_filter, cn, pff, cn, pff); - printf ("%s\n", buf); - system (buf); - pcc->generated_pf_file = true; - return OPENVPN_PLUGIN_FUNC_SUCCESS; - } - else - return OPENVPN_PLUGIN_FUNC_ERROR; - } - else - return OPENVPN_PLUGIN_FUNC_ERROR; - } - else - return OPENVPN_PLUGIN_FUNC_SUCCESS; -} - -OPENVPN_EXPORT int -openvpn_plugin_func_v2 (openvpn_plugin_handle_t handle, - const int type, - const char *argv[], - const char *envp[], - void *per_client_context, - struct openvpn_plugin_string_list **return_list) -{ - struct plugin_context *context = (struct plugin_context *) handle; - struct plugin_per_client_context *pcc = (struct plugin_per_client_context *) per_client_context; - switch (type) - { - case OPENVPN_PLUGIN_UP: - printf ("OPENVPN_PLUGIN_UP\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_DOWN: - printf ("OPENVPN_PLUGIN_DOWN\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_ROUTE_UP: - printf ("OPENVPN_PLUGIN_ROUTE_UP\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_IPCHANGE: - printf ("OPENVPN_PLUGIN_IPCHANGE\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_TLS_VERIFY: - printf ("OPENVPN_PLUGIN_TLS_VERIFY\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY: - printf ("OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY\n"); - return auth_user_pass_verify (context, pcc, argv, envp); - case OPENVPN_PLUGIN_CLIENT_CONNECT_V2: - printf ("OPENVPN_PLUGIN_CLIENT_CONNECT_V2\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_CLIENT_DISCONNECT: - printf ("OPENVPN_PLUGIN_CLIENT_DISCONNECT\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_LEARN_ADDRESS: - printf ("OPENVPN_PLUGIN_LEARN_ADDRESS\n"); - return OPENVPN_PLUGIN_FUNC_SUCCESS; - case OPENVPN_PLUGIN_TLS_FINAL: - printf ("OPENVPN_PLUGIN_TLS_FINAL\n"); - return tls_final (context, pcc, argv, envp); - case OPENVPN_PLUGIN_ENABLE_PF: - printf ("OPENVPN_PLUGIN_ENABLE_PF\n"); - if (context->test_packet_filter) - return OPENVPN_PLUGIN_FUNC_SUCCESS; - else - return OPENVPN_PLUGIN_FUNC_ERROR; - default: - printf ("OPENVPN_PLUGIN_?\n"); - return OPENVPN_PLUGIN_FUNC_ERROR; - } -} - -OPENVPN_EXPORT void * -openvpn_plugin_client_constructor_v1 (openvpn_plugin_handle_t handle) -{ - printf ("FUNC: openvpn_plugin_client_constructor_v1\n"); - return calloc (1, sizeof (struct plugin_per_client_context)); -} - -OPENVPN_EXPORT void -openvpn_plugin_client_destructor_v1 (openvpn_plugin_handle_t handle, void *per_client_context) -{ - printf ("FUNC: openvpn_plugin_client_destructor_v1\n"); - free (per_client_context); -} - -OPENVPN_EXPORT void -openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) -{ - struct plugin_context *context = (struct plugin_context *) handle; - printf ("FUNC: openvpn_plugin_close_v1\n"); - free (context); -} diff --git a/openvpn/src/plugins/defer/simple.def b/openvpn/src/plugins/defer/simple.def deleted file mode 100755 index a87507d1..00000000 --- a/openvpn/src/plugins/defer/simple.def +++ /dev/null @@ -1,6 +0,0 @@ -LIBRARY OpenVPN_PLUGIN_SAMPLE -DESCRIPTION "Sample OpenVPN plug-in module." -EXPORTS - openvpn_plugin_open_v1 @1 - openvpn_plugin_func_v1 @2 - openvpn_plugin_close_v1 @3 diff --git a/openvpn/src/plugins/defer/winbuild b/openvpn/src/plugins/defer/winbuild deleted file mode 100755 index 82927d96..00000000 --- a/openvpn/src/plugins/defer/winbuild +++ /dev/null @@ -1,18 +0,0 @@ -# -# Build an OpenVPN plugin module on Windows/MinGW. -# The argument should be the base name of the C source file -# (without the .c). -# - -# This directory is where we will look for openvpn-plugin.h -INCLUDE="-I../../../build" - -CC_FLAGS="-O2 -Wall" - -gcc -DBUILD_DLL $CC_FLAGS $INCLUDE -c $1.c -gcc --disable-stdcall-fixup -mdll -DBUILD_DLL -o junk.tmp -Wl,--base-file,base.tmp $1.o -rm junk.tmp -dlltool --dllname $1.dll --base-file base.tmp --output-exp temp.exp --input-def $1.def -rm base.tmp -gcc --enable-stdcall-fixup -mdll -DBUILD_DLL -o $1.dll $1.o -Wl,temp.exp -rm temp.exp diff --git a/openvpn/src/plugins/down-root/Makefile b/openvpn/src/plugins/down-root/Makefile deleted file mode 100755 index e66c99ae..00000000 --- a/openvpn/src/plugins/down-root/Makefile +++ /dev/null @@ -1,18 +0,0 @@ -# -# Build the OpenVPN down-root plugin module. -# - -# This directory is where we will look for openvpn-plugin.h -CPPFLAGS=-I../../../include - -CC=gcc -CFLAGS=-O2 -Wall - -down-root.so : down-root.o - $(CC) $(CFLAGS) -fPIC -shared $(LDFLAGS) -Wl,-soname,openvpn-down-root.so -o openvpn-down-root.so down-root.o -lc - -down-root.o : down-root.c - $(CC) $(CPPFLAGS) $(CFLAGS) -fPIC -c down-root.c - -clean : - -rm -f *.o *.so diff --git a/openvpn/src/plugins/down-root/Makefile.am b/openvpn/src/plugins/down-root/Makefile.am new file mode 100644 index 00000000..064aa30c --- /dev/null +++ b/openvpn/src/plugins/down-root/Makefile.am @@ -0,0 +1,23 @@ +# +# OpenVPN (TM) Down Root Plugin -- OpenVPN Plugin +# +# Copyright (C) 2012 Alon Bar-Lev +# + +MAINTAINERCLEANFILES = \ + $(srcdir)/Makefile.in + +AM_CFLAGS = \ + -I$(top_srcdir)/include + +if ENABLE_PLUGIN_DOWN_ROOT +plugin_LTLIBRARIES = openvpn-plugin-down-root.la +dist_doc_DATA = README.down-root +endif + +openvpn_plugin_down_root_la_SOURCES = \ + down-root.c \ + down-root.exports +openvpn_plugin_down_root_la_LDFLAGS = $(AM_LDFLAGS) \ + -export-symbols "$(srcdir)/down-root.exports" \ + -module -shared -avoid-version -no-undefined diff --git a/openvpn/src/plugins/down-root/README b/openvpn/src/plugins/down-root/README deleted file mode 100644 index d337ffe9..00000000 --- a/openvpn/src/plugins/down-root/README +++ /dev/null @@ -1,29 +0,0 @@ -down-root -- an OpenVPN Plugin Module - -SYNOPSIS - -The down-root module allows an OpenVPN configuration to -call a down script with root privileges, even when privileges -have been dropped using --user/--group/--chroot. - -This module uses a split privilege execution model which will -fork() before OpenVPN drops root privileges, at the point where -the --up script is usually called. The module will then remain -in a wait state until it receives a message from OpenVPN via -pipe to execute the down script. Thus, the down script will be -run in the same execution environment as the up script. - -BUILD - -Build this module with the "make" command. The plugin -module will be named openvpn-down-root.so - -USAGE - -To use this module, add to your OpenVPN config file: - - plugin openvpn-down-root.so "command ..." - -CAVEATS - -This module will only work on *nix systems, not Windows. diff --git a/openvpn/src/plugins/down-root/README.down-root b/openvpn/src/plugins/down-root/README.down-root new file mode 100644 index 00000000..d337ffe9 --- /dev/null +++ b/openvpn/src/plugins/down-root/README.down-root @@ -0,0 +1,29 @@ +down-root -- an OpenVPN Plugin Module + +SYNOPSIS + +The down-root module allows an OpenVPN configuration to +call a down script with root privileges, even when privileges +have been dropped using --user/--group/--chroot. + +This module uses a split privilege execution model which will +fork() before OpenVPN drops root privileges, at the point where +the --up script is usually called. The module will then remain +in a wait state until it receives a message from OpenVPN via +pipe to execute the down script. Thus, the down script will be +run in the same execution environment as the up script. + +BUILD + +Build this module with the "make" command. The plugin +module will be named openvpn-down-root.so + +USAGE + +To use this module, add to your OpenVPN config file: + + plugin openvpn-down-root.so "command ..." + +CAVEATS + +This module will only work on *nix systems, not Windows. diff --git a/openvpn/src/plugins/down-root/down-root.c b/openvpn/src/plugins/down-root/down-root.c index fced23be..d51d0e55 100644 --- a/openvpn/src/plugins/down-root/down-root.c +++ b/openvpn/src/plugins/down-root/down-root.c @@ -26,6 +26,10 @@ * OpenVPN plugin module to do privileged down-script execution. */ +#ifdef HAVE_CONFIG_H +#include +#endif + #include #include #include @@ -37,7 +41,7 @@ #include #include -#include "openvpn-plugin.h" +#include #define DEBUG(verb) ((verb) >= 7) diff --git a/openvpn/src/plugins/down-root/down-root.exports b/openvpn/src/plugins/down-root/down-root.exports new file mode 100644 index 00000000..b07937cc --- /dev/null +++ b/openvpn/src/plugins/down-root/down-root.exports @@ -0,0 +1,4 @@ +openvpn_plugin_open_v1 +openvpn_plugin_func_v1 +openvpn_plugin_close_v1 +openvpn_plugin_abort_v1 diff --git a/openvpn/src/plugins/examples/README b/openvpn/src/plugins/examples/README deleted file mode 100644 index 4400cd30..00000000 --- a/openvpn/src/plugins/examples/README +++ /dev/null @@ -1,16 +0,0 @@ -OpenVPN plugin examples. - -Examples provided: - -simple.c -- using the --auth-user-pass-verify callback, verify - that the username/password is "foo"/"bar". - -To build: - - ./build simple (Linux/BSD/etc.) - ./winbuild simple (MinGW on Windows) - -To use in OpenVPN, add to config file: - - plugin simple.so (Linux/BSD/etc.) - plugin simple.dll (MinGW on Windows) diff --git a/openvpn/src/plugins/examples/build b/openvpn/src/plugins/examples/build deleted file mode 100755 index bbb05f7c..00000000 --- a/openvpn/src/plugins/examples/build +++ /dev/null @@ -1,15 +0,0 @@ -#!/bin/sh - -# -# Build an OpenVPN plugin module on *nix. The argument should -# be the base name of the C source file (without the .c). -# - -# This directory is where we will look for openvpn-plugin.h -CPPFLAGS="${CPPFLAGS:--I../../..}" - -CC="${CC:-gcc}" -CFLAGS="${CFLAGS:--O2 -Wall -g}" - -$CC $CPPFLAGS $CFLAGS -fPIC -c $1.c && \ -$CC $CFLAGS -fPIC -shared $LDFLAGS -Wl,-soname,$1.so -o $1.so $1.o -lc diff --git a/openvpn/src/plugins/examples/log.c b/openvpn/src/plugins/examples/log.c deleted file mode 100644 index 1cc4650e..00000000 --- a/openvpn/src/plugins/examples/log.c +++ /dev/null @@ -1,184 +0,0 @@ -/* - * OpenVPN -- An application to securely tunnel IP networks - * over a single TCP/UDP port, with support for SSL/TLS-based - * session authentication and key exchange, - * packet encryption, packet authentication, and - * packet compression. - * - * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 - * as published by the Free Software Foundation. - * - * 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 (see the file COPYING included with this - * distribution); if not, write to the Free Software Foundation, Inc., - * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -/* - * This plugin is similar to simple.c, except it also logs extra information - * to stdout for every plugin method called by OpenVPN. - * - * See the README file for build instructions. - */ - -#include -#include -#include - -#include "openvpn-plugin.h" - -/* - * Our context, where we keep our state. - */ -struct plugin_context { - const char *username; - const char *password; -}; - -/* - * Given an environmental variable name, search - * the envp array for its value, returning it - * if found or NULL otherwise. - */ -static const char * -get_env (const char *name, const char *envp[]) -{ - if (envp) - { - int i; - const int namelen = strlen (name); - for (i = 0; envp[i]; ++i) - { - if (!strncmp (envp[i], name, namelen)) - { - const char *cp = envp[i] + namelen; - if (*cp == '=') - return cp + 1; - } - } - } - return NULL; -} - -OPENVPN_EXPORT openvpn_plugin_handle_t -openvpn_plugin_open_v1 (unsigned int *type_mask, const char *argv[], const char *envp[]) -{ - struct plugin_context *context; - - /* - * Allocate our context - */ - context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); - - /* - * Set the username/password we will require. - */ - context->username = "foo"; - context->password = "bar"; - - /* - * Which callbacks to intercept. - */ - *type_mask = - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_UP) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_DOWN) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ROUTE_UP) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_IPCHANGE) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_VERIFY) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_CONNECT_V2) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_DISCONNECT) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_LEARN_ADDRESS) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_FINAL); - - return (openvpn_plugin_handle_t) context; -} - -void -show (const int type, const char *argv[], const char *envp[]) -{ - size_t i; - switch (type) - { - case OPENVPN_PLUGIN_UP: - printf ("OPENVPN_PLUGIN_UP\n"); - break; - case OPENVPN_PLUGIN_DOWN: - printf ("OPENVPN_PLUGIN_DOWN\n"); - break; - case OPENVPN_PLUGIN_ROUTE_UP: - printf ("OPENVPN_PLUGIN_ROUTE_UP\n"); - break; - case OPENVPN_PLUGIN_IPCHANGE: - printf ("OPENVPN_PLUGIN_IPCHANGE\n"); - break; - case OPENVPN_PLUGIN_TLS_VERIFY: - printf ("OPENVPN_PLUGIN_TLS_VERIFY\n"); - break; - case OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY: - printf ("OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY\n"); - break; - case OPENVPN_PLUGIN_CLIENT_CONNECT_V2: - printf ("OPENVPN_PLUGIN_CLIENT_CONNECT_V2\n"); - break; - case OPENVPN_PLUGIN_CLIENT_DISCONNECT: - printf ("OPENVPN_PLUGIN_CLIENT_DISCONNECT\n"); - break; - case OPENVPN_PLUGIN_LEARN_ADDRESS: - printf ("OPENVPN_PLUGIN_LEARN_ADDRESS\n"); - break; - case OPENVPN_PLUGIN_TLS_FINAL: - printf ("OPENVPN_PLUGIN_TLS_FINAL\n"); - break; - default: - printf ("OPENVPN_PLUGIN_?\n"); - break; - } - - printf ("ARGV\n"); - for (i = 0; argv[i] != NULL; ++i) - printf ("%d '%s'\n", (int)i, argv[i]); - - printf ("ENVP\n"); - for (i = 0; envp[i] != NULL; ++i) - printf ("%d '%s'\n", (int)i, envp[i]); -} - -OPENVPN_EXPORT int -openvpn_plugin_func_v1 (openvpn_plugin_handle_t handle, const int type, const char *argv[], const char *envp[]) -{ - struct plugin_context *context = (struct plugin_context *) handle; - - show (type, argv, envp); - - /* check entered username/password against what we require */ - if (type == OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) - { - /* get username/password from envp string array */ - const char *username = get_env ("username", envp); - const char *password = get_env ("password", envp); - - if (username && !strcmp (username, context->username) - && password && !strcmp (password, context->password)) - return OPENVPN_PLUGIN_FUNC_SUCCESS; - else - return OPENVPN_PLUGIN_FUNC_ERROR; - } - else - return OPENVPN_PLUGIN_FUNC_SUCCESS; -} - -OPENVPN_EXPORT void -openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) -{ - struct plugin_context *context = (struct plugin_context *) handle; - free (context); -} diff --git a/openvpn/src/plugins/examples/log_v3.c b/openvpn/src/plugins/examples/log_v3.c deleted file mode 100644 index 742c7568..00000000 --- a/openvpn/src/plugins/examples/log_v3.c +++ /dev/null @@ -1,247 +0,0 @@ -/* - * OpenVPN -- An application to securely tunnel IP networks - * over a single TCP/UDP port, with support for SSL/TLS-based - * session authentication and key exchange, - * packet encryption, packet authentication, and - * packet compression. - * - * Copyright (C) 2002-2009 OpenVPN Technologies, Inc. - * Copyright (C) 2010 David Sommerseth - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 - * as published by the Free Software Foundation. - * - * 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 (see the file COPYING included with this - * distribution); if not, write to the Free Software Foundation, Inc., - * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -/* - * This plugin is similar to simple.c, except it also logs extra information - * to stdout for every plugin method called by OpenVPN. The only difference - * between this (log_v3.c) and log.c is that this module uses the v3 plug-in - * API. - * - * See the README file for build instructions. - */ - -#include -#include -#include - -#define ENABLE_SSL - -#include "openvpn-plugin.h" - -/* - * Our context, where we keep our state. - */ -struct plugin_context { - const char *username; - const char *password; -}; - -/* - * Given an environmental variable name, search - * the envp array for its value, returning it - * if found or NULL otherwise. - */ -static const char * -get_env (const char *name, const char *envp[]) -{ - if (envp) - { - int i; - const int namelen = strlen (name); - for (i = 0; envp[i]; ++i) - { - if (!strncmp (envp[i], name, namelen)) - { - const char *cp = envp[i] + namelen; - if (*cp == '=') - return cp + 1; - } - } - } - return NULL; -} - -OPENVPN_EXPORT int -openvpn_plugin_open_v3 (const int v3structver, - struct openvpn_plugin_args_open_in const *args, - struct openvpn_plugin_args_open_return *ret) -{ - struct plugin_context *context = NULL; - - /* Check that we are API compatible */ - if( v3structver != OPENVPN_PLUGINv3_STRUCTVER ) { - return OPENVPN_PLUGIN_FUNC_ERROR; - } - - /* Which callbacks to intercept. */ - ret->type_mask = - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_UP) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_DOWN) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_ROUTE_UP) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_IPCHANGE) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_VERIFY) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_CONNECT_V2) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_CLIENT_DISCONNECT) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_LEARN_ADDRESS) | - OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_TLS_FINAL); - - - /* Allocate our context */ - context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); - - /* Set the username/password we will require. */ - context->username = "foo"; - context->password = "bar"; - - /* Point the global context handle to our newly created context */ - ret->handle = (void *) context; - - return OPENVPN_PLUGIN_FUNC_SUCCESS; -} - -void -show (const int type, const char *argv[], const char *envp[]) -{ - size_t i; - switch (type) - { - case OPENVPN_PLUGIN_UP: - printf ("OPENVPN_PLUGIN_UP\n"); - break; - case OPENVPN_PLUGIN_DOWN: - printf ("OPENVPN_PLUGIN_DOWN\n"); - break; - case OPENVPN_PLUGIN_ROUTE_UP: - printf ("OPENVPN_PLUGIN_ROUTE_UP\n"); - break; - case OPENVPN_PLUGIN_IPCHANGE: - printf ("OPENVPN_PLUGIN_IPCHANGE\n"); - break; - case OPENVPN_PLUGIN_TLS_VERIFY: - printf ("OPENVPN_PLUGIN_TLS_VERIFY\n"); - break; - case OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY: - printf ("OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY\n"); - break; - case OPENVPN_PLUGIN_CLIENT_CONNECT_V2: - printf ("OPENVPN_PLUGIN_CLIENT_CONNECT_V2\n"); - break; - case OPENVPN_PLUGIN_CLIENT_DISCONNECT: - printf ("OPENVPN_PLUGIN_CLIENT_DISCONNECT\n"); - break; - case OPENVPN_PLUGIN_LEARN_ADDRESS: - printf ("OPENVPN_PLUGIN_LEARN_ADDRESS\n"); - break; - case OPENVPN_PLUGIN_TLS_FINAL: - printf ("OPENVPN_PLUGIN_TLS_FINAL\n"); - break; - default: - printf ("OPENVPN_PLUGIN_?\n"); - break; - } - - printf ("ARGV\n"); - for (i = 0; argv[i] != NULL; ++i) - printf ("%d '%s'\n", (int)i, argv[i]); - - printf ("ENVP\n"); - for (i = 0; envp[i] != NULL; ++i) - printf ("%d '%s'\n", (int)i, envp[i]); -} - -static void -x509_print_info (X509 *x509crt) -{ - int i, n; - int fn_nid; - ASN1_OBJECT *fn; - ASN1_STRING *val; - X509_NAME *x509_name; - X509_NAME_ENTRY *ent; - const char *objbuf; - unsigned char *buf; - - x509_name = X509_get_subject_name (x509crt); - n = X509_NAME_entry_count (x509_name); - for (i = 0; i < n; ++i) - { - ent = X509_NAME_get_entry (x509_name, i); - if (!ent) - continue; - fn = X509_NAME_ENTRY_get_object (ent); - if (!fn) - continue; - val = X509_NAME_ENTRY_get_data (ent); - if (!val) - continue; - fn_nid = OBJ_obj2nid (fn); - if (fn_nid == NID_undef) - continue; - objbuf = OBJ_nid2sn (fn_nid); - if (!objbuf) - continue; - buf = (unsigned char *)1; /* bug in OpenSSL 0.9.6b ASN1_STRING_to_UTF8 requires this workaround */ - if (ASN1_STRING_to_UTF8 (&buf, val) <= 0) - continue; - - printf("X509 %s: %s\n", objbuf, (char *)buf); - OPENSSL_free (buf); - } -} - - - -OPENVPN_EXPORT int -openvpn_plugin_func_v3 (const int version, - struct openvpn_plugin_args_func_in const *args, - struct openvpn_plugin_args_func_return *retptr) -{ - struct plugin_context *context = (struct plugin_context *) args->handle; - - printf("\nopenvpn_plugin_func_v3() :::::>> "); - show (args->type, args->argv, args->envp); - - /* Dump some X509 information if we're in the TLS_VERIFY phase */ - if ((args->type == OPENVPN_PLUGIN_TLS_VERIFY) && args->current_cert ) { - printf("---- X509 Subject information ----\n"); - printf("Certificate depth: %i\n", args->current_cert_depth); - x509_print_info(args->current_cert); - printf("----------------------------------\n"); - } - - /* check entered username/password against what we require */ - if (args->type == OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY) - { - /* get username/password from envp string array */ - const char *username = get_env ("username", args->envp); - const char *password = get_env ("password", args->envp); - - if (username && !strcmp (username, context->username) - && password && !strcmp (password, context->password)) - return OPENVPN_PLUGIN_FUNC_SUCCESS; - else - return OPENVPN_PLUGIN_FUNC_ERROR; - } - else - return OPENVPN_PLUGIN_FUNC_SUCCESS; -} - -OPENVPN_EXPORT void -openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) -{ - struct plugin_context *context = (struct plugin_context *) handle; - free (context); -} diff --git a/openvpn/src/plugins/examples/simple.c b/openvpn/src/plugins/examples/simple.c deleted file mode 100644 index f26d89f6..00000000 --- a/openvpn/src/plugins/examples/simple.c +++ /dev/null @@ -1,120 +0,0 @@ -/* - * OpenVPN -- An application to securely tunnel IP networks - * over a single TCP/UDP port, with support for SSL/TLS-based - * session authentication and key exchange, - * packet encryption, packet authentication, and - * packet compression. - * - * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 - * as published by the Free Software Foundation. - * - * 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 (see the file COPYING included with this - * distribution); if not, write to the Free Software Foundation, Inc., - * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -/* - * This file implements a simple OpenVPN plugin module which - * will examine the username/password provided by a client, - * and make an accept/deny determination. Will run - * on Windows or *nix. - * - * See the README file for build instructions. - */ - -#include -#include -#include - -#include "openvpn-plugin.h" - -/* - * Our context, where we keep our state. - */ -struct plugin_context { - const char *username; - const char *password; -}; - -/* - * Given an environmental variable name, search - * the envp array for its value, returning it - * if found or NULL otherwise. - */ -static const char * -get_env (const char *name, const char *envp[]) -{ - if (envp) - { - int i; - const int namelen = strlen (name); - for (i = 0; envp[i]; ++i) - { - if (!strncmp (envp[i], name, namelen)) - { - const char *cp = envp[i] + namelen; - if (*cp == '=') - return cp + 1; - } - } - } - return NULL; -} - -OPENVPN_EXPORT openvpn_plugin_handle_t -openvpn_plugin_open_v1 (unsigned int *type_mask, const char *argv[], const char *envp[]) -{ - struct plugin_context *context; - - /* - * Allocate our context - */ - context = (struct plugin_context *) calloc (1, sizeof (struct plugin_context)); - - /* - * Set the username/password we will require. - */ - context->username = "foo"; - context->password = "bar"; - - /* - * We are only interested in intercepting the - * --auth-user-pass-verify callback. - */ - *type_mask = OPENVPN_PLUGIN_MASK (OPENVPN_PLUGIN_AUTH_USER_PASS_VERIFY); - - return (openvpn_plugin_handle_t) context; -} - -OPENVPN_EXPORT int -openvpn_plugin_func_v1 (openvpn_plugin_handle_t handle, const int type, const char *argv[], const char *envp[]) -{ - struct plugin_context *context = (struct plugin_context *) handle; - - /* get username/password from envp string array */ - const char *username = get_env ("username", envp); - const char *password = get_env ("password", envp); - - /* check entered username/password against what we require */ - if (username && !strcmp (username, context->username) - && password && !strcmp (password, context->password)) - return OPENVPN_PLUGIN_FUNC_SUCCESS; - else - return OPENVPN_PLUGIN_FUNC_ERROR; -} - -OPENVPN_EXPORT void -openvpn_plugin_close_v1 (openvpn_plugin_handle_t handle) -{ - struct plugin_context *context = (struct plugin_context *) handle; - free (context); -} diff --git a/openvpn/src/plugins/examples/simple.def b/openvpn/src/plugins/examples/simple.def deleted file mode 100755 index a87507d1..00000000 --- a/openvpn/src/plugins/examples/simple.def +++ /dev/null @@ -1,6 +0,0 @@ -LIBRARY OpenVPN_PLUGIN_SAMPLE -DESCRIPTION "Sample OpenVPN plug-in module." -EXPORTS - openvpn_plugin_open_v1 @1 - openvpn_plugin_func_v1 @2 - openvpn_plugin_close_v1 @3 diff --git a/openvpn/src/plugins/examples/winbuild b/openvpn/src/plugins/examples/winbuild deleted file mode 100755 index decf05f8..00000000 --- a/openvpn/src/plugins/examples/winbuild +++ /dev/null @@ -1,18 +0,0 @@ -# -# Build an OpenVPN plugin module on Windows/MinGW. -# The argument should be the base name of the C source file -# (without the .c). -# - -# This directory is where we will look for openvpn-plugin.h -INCLUDE="-I../../../include" - -CC_FLAGS="-O2 -Wall" - -gcc -DBUILD_DLL $CC_FLAGS $INCLUDE -c $1.c -gcc --disable-stdcall-fixup -mdll -DBUILD_DLL -o junk.tmp -Wl,--base-file,base.tmp $1.o -rm junk.tmp -dlltool --dllname $1.dll --base-file base.tmp --output-exp temp.exp --input-def $1.def -rm base.tmp -gcc --enable-stdcall-fixup -mdll -DBUILD_DLL -o $1.dll $1.o -Wl,temp.exp -rm temp.exp diff --git a/openvpn/tests/t_client.sh.in b/openvpn/tests/t_client.sh.in index d58b8210..8c66033f 100755 --- a/openvpn/tests/t_client.sh.in +++ b/openvpn/tests/t_client.sh.in @@ -91,7 +91,7 @@ get_ifconfig_route() echo "-- linux iproute2 --" @IPROUTE@ addr show | grep -v valid_lft @IPROUTE@ route show - @IPROUTE@ -o -6 route show | grep -v ' cache' | sed -e 's/expires [0-9]*sec //' + @IPROUTE@ -o -6 route show | grep -v ' cache' | sed -e 's/expires [0-9]*sec//' return fi @@ -203,6 +203,9 @@ run_ping_tests() # ---------------------------------------------------------- # main test loop # ---------------------------------------------------------- +SUMMARY_OK= +SUMMARY_FAIL= + for SUF in $TEST_RUN_LIST do # get config variables @@ -294,12 +297,19 @@ do fi if [ "$fail_count" = 0 ] ; then echo -e "test run $SUF: all tests OK.\n" + SUMMARY_OK="$SUMMARY_OK $SUF" else echo -e "test run $SUF: $fail_count test failures. FAIL.\n"; + SUMMARY_FAIL="$SUMMARY_FAIL $SUF" exit_code=30 fi done +if [ -z "$SUMMARY_OK" ] ; then SUMMARY_OK=" none"; fi +if [ -z "$SUMMARY_FAIL" ] ; then SUMMARY_FAIL=" none"; fi +echo "Test sets succeded:$SUMMARY_OK." +echo "Test sets failed:$SUMMARY_FAIL." + # remove trap handler trap - 0 1 2 3 15 exit $exit_code diff --git a/openvpn/version.m4 b/openvpn/version.m4 index 1ea1c32f..f3f4511e 100644 --- a/openvpn/version.m4 +++ b/openvpn/version.m4 @@ -1,7 +1,7 @@ dnl define the OpenVPN version define([PRODUCT_NAME], [OpenVPN]) define([PRODUCT_TARNAME], [openvpn]) -define([PRODUCT_VERSION], [2.3_master]) +define([PRODUCT_VERSION], [2.3_alpha3]) define([PRODUCT_BUGREPORT], [openvpn-users@lists.sourceforge.net]) define([PRODUCT_VERSION_RESOURCE], [2,3,0,0]) dnl define the TAP version -- cgit v1.2.3