use libcap for capability dropping
optional, must be enabled --with-capabilities=libcap will be extended to support --with-capabilities=libcap2
This commit is contained in:
parent
8fa6f2dc66
commit
eb3e27059b
26
configure.in
26
configure.in
|
@ -138,6 +138,14 @@ AC_ARG_WITH(
|
|||
[AC_SUBST(ipsecgroup, "root")]
|
||||
)
|
||||
|
||||
dnl Will be extended to --with-capabilities=libcap|libcap2
|
||||
AC_ARG_WITH(
|
||||
[capabilities],
|
||||
AS_HELP_STRING([--with-capabilities=libcap],[capability dropping using libcap. Currenlty only the value "libcap" is supported (default is NO).]),
|
||||
[capabilities="$withval"],
|
||||
[capabilities=no]
|
||||
)
|
||||
|
||||
AC_ARG_ENABLE(
|
||||
[curl],
|
||||
AS_HELP_STRING([--enable-curl],[enable CURL fetcher plugin to fetch files via libcurl (default is NO). Requires libcurl.]),
|
||||
|
@ -628,15 +636,6 @@ AC_HAVE_LIBRARY(dl)
|
|||
AC_CHECK_FUNCS(backtrace)
|
||||
AC_CHECK_FUNCS(dladdr)
|
||||
|
||||
AC_MSG_CHECKING([capset() definition])
|
||||
AC_TRY_COMPILE(
|
||||
[#include <linux/capset.h>],
|
||||
[
|
||||
void *test = capset;
|
||||
],
|
||||
[AC_MSG_RESULT([yes])], [AC_MSG_RESULT([no]); AC_DEFINE_UNQUOTED(NO_CAPSET_DEFINED, 1)]
|
||||
)
|
||||
|
||||
if test x$gmp = xtrue; then
|
||||
AC_HAVE_LIBRARY([gmp],[LIBS="$LIBS"],[AC_MSG_ERROR([GNU Multi Precision library gmp not found])])
|
||||
AC_MSG_CHECKING([gmp.h version >= 4.1.4])
|
||||
|
@ -732,6 +731,11 @@ if test x$eap_gtc = xtrue; then
|
|||
AC_CHECK_HEADER([security/pam_appl.h],,[AC_MSG_ERROR([PAM header security/pam_appl.h not found!])])
|
||||
fi
|
||||
|
||||
if test x$capabilities = xlibcap; then
|
||||
AC_HAVE_LIBRARY([cap],[LIBS="$LIBS"],[AC_MSG_ERROR([libcap library not found])])
|
||||
AC_CHECK_HEADER([sys/capability.h],,[AC_MSG_ERROR([libcap header sys/capability.h not found!])])
|
||||
fi
|
||||
|
||||
dnl ======================================
|
||||
dnl collect all plugins for libstrongswan
|
||||
dnl ======================================
|
||||
|
@ -850,6 +854,7 @@ AM_CONDITIONAL(USE_MANAGER, test x$manager = xtrue)
|
|||
AM_CONDITIONAL(USE_ME, test x$me = xtrue)
|
||||
AM_CONDITIONAL(USE_INTEGRITY_TEST, test x$integrity_test = xtrue)
|
||||
AM_CONDITIONAL(USE_SELF_TEST, test x$self_test = xtrue)
|
||||
AM_CONDITIONAL(USE_CAPABILITIES, test x$capabilities = xlibcap)
|
||||
AM_CONDITIONAL(USE_PLUTO, test x$pluto = xtrue)
|
||||
AM_CONDITIONAL(USE_CHARON, test x$charon = xtrue)
|
||||
AM_CONDITIONAL(USE_TOOLS, test x$tools = xtrue)
|
||||
|
@ -864,6 +869,9 @@ dnl ==============================
|
|||
if test x$me = xtrue; then
|
||||
AC_DEFINE(ME)
|
||||
fi
|
||||
if test x$capabilities = xlibcap; then
|
||||
AC_DEFINE(CAPABILITIES)
|
||||
fi
|
||||
|
||||
dnl ==============================
|
||||
dnl build Makefiles
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
#!/bin/bash
|
||||
CFLAGS="-Wall -Wno-format -Wno-pointer-sign -Wno-strict-aliasing -g -O2" ./configure \
|
||||
--sysconfdir=/etc --disable-tools --disable-pluto --enable-leak-detective --enable-dumm \
|
||||
--sysconfdir=/etc --disable-tools --disable-pluto --enable-leak-detective --enable-dumm --with-capabilities=libcap \
|
||||
$1 $2 $3 $4 $5
|
||||
|
|
|
@ -129,6 +129,11 @@ if USE_SELF_TEST
|
|||
AM_CFLAGS += -DSELF_TEST
|
||||
endif
|
||||
|
||||
if USE_CAPABILITIES
|
||||
charon_LDADD += -lcap
|
||||
endif
|
||||
|
||||
|
||||
# build optional plugins
|
||||
########################
|
||||
|
||||
|
|
|
@ -22,7 +22,6 @@
|
|||
#endif /* HAVE_DLADDR */
|
||||
|
||||
#include <stdio.h>
|
||||
#include <linux/capability.h>
|
||||
#include <sys/prctl.h>
|
||||
#include <signal.h>
|
||||
#include <pthread.h>
|
||||
|
@ -38,6 +37,9 @@
|
|||
#ifdef HAVE_BACKTRACE
|
||||
# include <execinfo.h>
|
||||
#endif /* HAVE_BACKTRACE */
|
||||
#ifdef CAPABILITIES
|
||||
#include <sys/capability.h>
|
||||
#endif /* CAPABILITIES */
|
||||
|
||||
#include "daemon.h"
|
||||
|
||||
|
@ -45,16 +47,6 @@
|
|||
#include <config/traffic_selector.h>
|
||||
#include <config/proposal.h>
|
||||
|
||||
/* on some distros, a capset definition is missing */
|
||||
#ifdef NO_CAPSET_DEFINED
|
||||
extern int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
|
||||
#endif /* NO_CAPSET_DEFINED */
|
||||
|
||||
/* missing on older kernel headers */
|
||||
#ifndef CAP_AUDIT_WRITE
|
||||
#define CAP_AUDIT_WRITE 29
|
||||
#endif /* CAP_AUDIT_WRITE */
|
||||
|
||||
#ifdef INTEGRITY_TEST
|
||||
#include <fips/fips.h>
|
||||
#include <fips/fips_signature.h>
|
||||
|
@ -80,11 +72,13 @@ struct private_daemon_t {
|
|||
* The thread_id of main-thread.
|
||||
*/
|
||||
pthread_t main_thread_id;
|
||||
|
||||
|
||||
#ifdef CAPABILITIES
|
||||
/**
|
||||
* capabilities to keep
|
||||
*/
|
||||
u_int32_t keep;
|
||||
cap_t caps;
|
||||
#endif /* CAPABILITIES */
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -193,6 +187,9 @@ static void destroy(private_daemon_t *this)
|
|||
}
|
||||
/* unload plugins to release threads */
|
||||
lib->plugins->unload(lib->plugins);
|
||||
#ifdef CAPABILITIES
|
||||
cap_free(this->caps);
|
||||
#endif /* CAPABILITIES */
|
||||
DESTROY_IF(this->public.ike_sa_manager);
|
||||
DESTROY_IF(this->public.kernel_interface);
|
||||
DESTROY_IF(this->public.scheduler);
|
||||
|
@ -253,10 +250,7 @@ static void kill_daemon(private_daemon_t *this, char *reason)
|
|||
* drop daemon capabilities
|
||||
*/
|
||||
static void drop_capabilities(private_daemon_t *this)
|
||||
{
|
||||
struct __user_cap_header_struct hdr;
|
||||
struct __user_cap_data_struct data;
|
||||
|
||||
{
|
||||
prctl(PR_SET_KEEPCAPS, 1);
|
||||
|
||||
if (setgid(charon->gid) != 0)
|
||||
|
@ -267,21 +261,13 @@ static void drop_capabilities(private_daemon_t *this)
|
|||
{
|
||||
kill_daemon(this, "change to unprivileged user failed");
|
||||
}
|
||||
|
||||
/* we use the old capset version for now. For systems with version 2
|
||||
* available, we specifiy version 1 excplicitly. */
|
||||
#ifdef _LINUX_CAPABILITY_VERSION_1
|
||||
hdr.version = _LINUX_CAPABILITY_VERSION_1;
|
||||
#else
|
||||
hdr.version = _LINUX_CAPABILITY_VERSION;
|
||||
#endif
|
||||
hdr.pid = 0;
|
||||
data.inheritable = data.effective = data.permitted = this->keep;
|
||||
|
||||
if (capset(&hdr, &data))
|
||||
#ifdef CAPABILITIES
|
||||
if (cap_set_proc(this->caps) != 0)
|
||||
{
|
||||
kill_daemon(this, "unable to drop daemon capabilities");
|
||||
}
|
||||
#endif /* CAPABILITIES */
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -289,7 +275,11 @@ static void drop_capabilities(private_daemon_t *this)
|
|||
*/
|
||||
static void keep_cap(private_daemon_t *this, u_int cap)
|
||||
{
|
||||
this->keep |= 1 << cap;
|
||||
#ifdef CAPABILITIES
|
||||
cap_set_flag(this->caps, CAP_EFFECTIVE, 1, &cap, CAP_SET);
|
||||
cap_set_flag(this->caps, CAP_INHERITABLE, 1, &cap, CAP_SET);
|
||||
cap_set_flag(this->caps, CAP_PERMITTED, 1, &cap, CAP_SET);
|
||||
#endif /* CAPABILITIES */
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -498,11 +488,14 @@ private_daemon_t *daemon_create(void)
|
|||
this->public.gid = 0;
|
||||
|
||||
this->main_thread_id = pthread_self();
|
||||
this->keep = 1<<CAP_NET_ADMIN;
|
||||
#ifdef CAPABILITIES
|
||||
this->caps = cap_init();
|
||||
keep_cap(this, CAP_NET_ADMIN);
|
||||
if (lib->leak_detective)
|
||||
{
|
||||
this->keep = 1<<CAP_SYS_NICE;
|
||||
keep_cap(this, CAP_SYS_NICE);
|
||||
}
|
||||
#endif /* CAPABILITIES */
|
||||
|
||||
/* add handler for SEGV and ILL,
|
||||
* add handler for USR1 (cancellation).
|
||||
|
|
|
@ -21,7 +21,8 @@
|
|||
|
||||
#include <daemon.h>
|
||||
|
||||
#include <linux/capability.h>
|
||||
/* missing in cababilities.h */
|
||||
#define CAP_AUDIT_WRITE 29
|
||||
|
||||
/**
|
||||
* Implementation of plugin_t.destroy
|
||||
|
|
|
@ -139,3 +139,7 @@ if USE_SMARTCARD
|
|||
AM_CFLAGS += -DSMARTCARD
|
||||
endif
|
||||
|
||||
if USE_CAPABILITIES
|
||||
pluto_LDADD += -lcap
|
||||
endif
|
||||
|
||||
|
|
|
@ -29,11 +29,14 @@
|
|||
#include <resolv.h>
|
||||
#include <arpa/nameser.h> /* missing from <resolv.h> on old systems */
|
||||
#include <sys/queue.h>
|
||||
#include <linux/capability.h>
|
||||
#include <sys/prctl.h>
|
||||
#include <pwd.h>
|
||||
#include <grp.h>
|
||||
|
||||
#ifdef CAPABILITIES
|
||||
#include <sys/capability.h>
|
||||
#endif /* CAPABILITIES */
|
||||
|
||||
#include <freeswan.h>
|
||||
|
||||
#include <pfkeyv2.h>
|
||||
|
@ -68,11 +71,6 @@
|
|||
#include "nat_traversal.h"
|
||||
#include "virtual.h"
|
||||
|
||||
/* on some distros, a capset() definition is missing */
|
||||
#ifdef NO_CAPSET_DEFINED
|
||||
extern int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
|
||||
#endif /* NO_CAPSET_DEFINED */
|
||||
|
||||
static void
|
||||
usage(const char *mess)
|
||||
{
|
||||
|
@ -236,8 +234,10 @@ main(int argc, char **argv)
|
|||
bool force_keepalive = FALSE;
|
||||
char *virtual_private = NULL;
|
||||
int lockfd;
|
||||
struct __user_cap_header_struct hdr;
|
||||
struct __user_cap_data_struct data;
|
||||
#ifdef CAPABILITIES
|
||||
cap_t caps;
|
||||
int keep[] = { CAP_NET_ADMIN, CAP_NET_BIND_SERVICE };
|
||||
#endif /* CAPABILITIES */
|
||||
|
||||
/* handle arguments */
|
||||
for (;;)
|
||||
|
@ -619,14 +619,6 @@ main(int argc, char **argv)
|
|||
init_fetch();
|
||||
|
||||
/* drop unneeded capabilities and change UID/GID */
|
||||
#ifdef _LINUX_CAPABILITY_VERSION_1
|
||||
hdr.version = _LINUX_CAPABILITY_VERSION_1;
|
||||
#else
|
||||
hdr.version = _LINUX_CAPABILITY_VERSION;
|
||||
#endif
|
||||
hdr.pid = 0;
|
||||
data.inheritable = data.effective = data.permitted =
|
||||
1<<CAP_NET_ADMIN | 1<<CAP_NET_BIND_SERVICE;
|
||||
|
||||
prctl(PR_SET_KEEPCAPS, 1);
|
||||
|
||||
|
@ -656,11 +648,19 @@ main(int argc, char **argv)
|
|||
}
|
||||
}
|
||||
#endif
|
||||
if (capset(&hdr, &data))
|
||||
|
||||
#ifdef CAPABILITIES
|
||||
caps = cap_init();
|
||||
cap_set_flag(caps, CAP_EFFECTIVE, 2, keep, CAP_SET);
|
||||
cap_set_flag(caps, CAP_INHERITABLE, 2, keep, CAP_SET);
|
||||
cap_set_flag(caps, CAP_PERMITTED, 2, keep, CAP_SET);
|
||||
if (cap_set_proc(caps) != 0)
|
||||
{
|
||||
plog("unable to drop root privileges");
|
||||
plog("unable to drop daemon capabilities");
|
||||
abort();
|
||||
}
|
||||
cap_free(caps);
|
||||
#endif /* CAPABILITIES */
|
||||
|
||||
/* loading X.509 CA certificates */
|
||||
load_authcerts("CA cert", CA_CERT_PATH, AUTH_CA);
|
||||
|
|
Loading…
Reference in New Issue