diff --git a/daemon/Makefile.am b/daemon/Makefile.am index fca0eacf7e..e8a8371585 100644 --- a/daemon/Makefile.am +++ b/daemon/Makefile.am @@ -24,6 +24,7 @@ INCLUDES = \ -I$(top_srcdir)/src/conf \ -I$(top_srcdir)/src/rpc \ -I$(top_srcdir)/src/remote \ + -I$(top_srcdir)/src/access \ $(GETTEXT_CPPFLAGS) CLEANFILES = diff --git a/daemon/libvirtd-config.c b/daemon/libvirtd-config.c index d9357b7470..6f60256e47 100644 --- a/daemon/libvirtd-config.c +++ b/daemon/libvirtd-config.c @@ -379,6 +379,10 @@ daemonConfigLoadOptions(struct daemonConfig *data, if (remoteConfigGetAuth(conf, "auth_tls", &data->auth_tls, filename) < 0) goto error; + if (remoteConfigGetStringList(conf, "access_drivers", + &data->access_drivers, filename) < 0) + goto error; + GET_CONF_STR(conf, filename, unix_sock_group); GET_CONF_STR(conf, filename, unix_sock_ro_perms); GET_CONF_STR(conf, filename, unix_sock_rw_perms); diff --git a/daemon/libvirtd-config.h b/daemon/libvirtd-config.h index 07118de408..973e0eab74 100644 --- a/daemon/libvirtd-config.h +++ b/daemon/libvirtd-config.h @@ -45,6 +45,8 @@ struct daemonConfig { int auth_tcp; int auth_tls; + char **access_drivers; + int mdns_adv; char *mdns_name; diff --git a/daemon/libvirtd.aug b/daemon/libvirtd.aug index f32b3a1397..7c56a41112 100644 --- a/daemon/libvirtd.aug +++ b/daemon/libvirtd.aug @@ -51,6 +51,7 @@ module Libvirtd = | bool_entry "tls_no_sanity_certificate" | str_array_entry "tls_allowed_dn_list" | str_array_entry "sasl_allowed_username_list" + | str_array_entry "access_drivers" let processing_entry = int_entry "min_workers" | int_entry "max_workers" diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c index ae6a15c7bd..3db4f1cdf8 100644 --- a/daemon/libvirtd.c +++ b/daemon/libvirtd.c @@ -52,8 +52,9 @@ #include "remote.h" #include "virhook.h" #include "viraudit.h" -#include "locking/lock_manager.h" #include "virstring.h" +#include "locking/lock_manager.h" +#include "viraccessmanager.h" #ifdef WITH_DRIVER_MODULES # include "driver.h" @@ -728,6 +729,26 @@ error: } +static int +daemonSetupAccessManager(struct daemonConfig *config) +{ + virAccessManagerPtr mgr; + const char *none[] = { "none", NULL }; + const char **driver = (const char **)config->access_drivers; + + if (!driver || + !driver[0]) + driver = none; + + if (!(mgr = virAccessManagerNewStack(driver))) + return -1; + + virAccessManagerSetDefault(mgr); + virObjectUnref(mgr); + return 0; +} + + /* Display version information. */ static void daemonVersion(const char *argv0) @@ -872,6 +893,9 @@ handleSystemMessageFunc(DBusConnection *connection ATTRIBUTE_UNUSED, static void daemonRunStateInit(void *opaque) { virNetServerPtr srv = opaque; + virIdentityPtr sysident = virIdentityGetSystem(); + + virIdentitySetCurrent(sysident); /* Since driver initialization can take time inhibit daemon shutdown until we're done so clients get a chance to connect */ @@ -914,6 +938,8 @@ static void daemonRunStateInit(void *opaque) cleanup: daemonInhibitCallback(false, srv); virObjectUnref(srv); + virObjectUnref(sysident); + virIdentitySetCurrent(NULL); } static int daemonStateInit(virNetServerPtr srv) @@ -1260,6 +1286,11 @@ int main(int argc, char **argv) { exit(EXIT_FAILURE); } + if (daemonSetupAccessManager(config) < 0) { + VIR_ERROR(_("Can't initialize access manager")); + exit(EXIT_FAILURE); + } + if (!pid_file && daemonPidFilePath(privileged, &pid_file) < 0) { diff --git a/daemon/libvirtd.conf b/daemon/libvirtd.conf index 47da5208eb..9d7879c982 100644 --- a/daemon/libvirtd.conf +++ b/daemon/libvirtd.conf @@ -155,6 +155,15 @@ #auth_tls = "none" +# Change the API access control scheme +# +# By default an authenticated user is allowed access +# to all APIs. Access drivers can place restrictions +# on this. By default the 'nop' driver is enabled, +# meaning no access control checks are done once a +# client has authenticated with libvirtd +# +#access_drivers = [ ] ################################################################# # diff --git a/daemon/test_libvirtd.aug.in b/daemon/test_libvirtd.aug.in index 455b74a196..b9df7117bd 100644 --- a/daemon/test_libvirtd.aug.in +++ b/daemon/test_libvirtd.aug.in @@ -17,6 +17,8 @@ module Test_libvirtd = { "auth_unix_rw" = "none" } { "auth_tcp" = "sasl" } { "auth_tls" = "none" } + { "access_drivers" + } { "key_file" = "/etc/pki/libvirt/private/serverkey.pem" } { "cert_file" = "/etc/pki/libvirt/servercert.pem" } { "ca_file" = "/etc/pki/CA/cacert.pem" } diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 9217ab90a4..9401d93c66 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1388,9 +1388,12 @@ virHookPresent; # util/viridentity.h virIdentityGetAttr; +virIdentityGetCurrent; +virIdentityGetSystem; virIdentityIsEqual; virIdentityNew; virIdentitySetAttr; +virIdentitySetCurrent; # util/virinitctl.h