diff --git a/docs/drvqemu.html.in b/docs/drvqemu.html.in index 294117ee1f161d312f0685a69d88f02a9eaeb2f6..8beb28655c0f84f97bfe6f4749195fcc5dd0a51e 100644 --- a/docs/drvqemu.html.in +++ b/docs/drvqemu.html.in @@ -187,41 +187,29 @@ chmod o+x /path/to/directory -

Linux process capabilities

-

- The libvirt QEMU driver has a build time option allowing it to use - the libcap-ng - library to manage process capabilities. If this build option is - enabled, then the QEMU driver will use this to ensure that all - process capabilities are dropped before executing a QEMU virtual - machine. Process capabilities are what gives the 'root' account - its high power, in particular the CAP_DAC_OVERRIDE capability - is what allows a process running as 'root' to access files owned - by any user. + The libvirt maintainers strongly recommend against + running QEMU as the root user/group. This should not be required + in most supported usage scenarios, as libvirt will generally do the + right thing to grant QEMU access to files it is permitted to + use when it is running non-root.

+

Linux process capabilities

+

- If the QEMU driver is configured to run virtual machines as non-root, - then they will already lose all their process capabilities at time - of startup. The Linux capability feature is thus aimed primarily at - the scenario where the QEMU processes are running as root. In this - case, before launching a QEMU virtual machine, libvirtd will use - libcap-ng APIs to drop all process capabilities. It is important - for administrators to note that this implies the QEMU process will - only be able to access files owned by root, and - not files owned by any other user. + In versions of libvirt prior to 6.0.0, even if QEMU was configured + to run as the root user / group, libvirt would strip all process + capabilities. This meant that QEMU could only read/write files + owned by root, or with open permissions. In reality, stripping + capabilities did not have any security benefit, as it was trivial + to get commands to run in another context with full capabilities, + for example, by creating a cronjob.

-

- Thus, if a vendor / distributor has configured their libvirt package - to run as 'qemu' by default, a number of changes will be required - before an administrator can change a host to run guests as root. - In particular it will be necessary to change ownership on the - directories /var/run/libvirt/qemu/, - /var/lib/libvirt/qemu/ and - /var/cache/libvirt/qemu/ back to root, in addition - to changing the /etc/libvirt/qemu.conf settings. + Thus since 6.0.0, if QEMU is running as root, it will keep all + process capabilities. Behaviour when QEMU is running non-root + is unchanged, it still has no capabilities.

SELinux basic confinement

diff --git a/src/qemu/libvirtd_qemu.aug b/src/qemu/libvirtd_qemu.aug index 7d7844dc09a23d0e08ad582827f2743c30339e78..86bea2a32a6c15a4caa74f31324e1e60011af1f0 100644 --- a/src/qemu/libvirtd_qemu.aug +++ b/src/qemu/libvirtd_qemu.aug @@ -86,7 +86,6 @@ module Libvirtd_qemu = | bool_entry "auto_start_bypass_cache" let process_entry = str_entry "hugetlbfs_mount" - | bool_entry "clear_emulator_capabilities" | str_entry "bridge_helper" | str_entry "pr_helper" | str_entry "slirp_helper" @@ -129,6 +128,12 @@ module Libvirtd_qemu = let swtpm_entry = str_entry "swtpm_user" | str_entry "swtpm_group" + (* Entries that used to exist in the config which are now + * deleted. We keep on parsing them so we don't break + * ability to parse old configs after upgrade + *) + let obsolete_entry = bool_entry "clear_emulator_capabilities" + let capability_filters_entry = str_array_entry "capability_filters" (* Each entry in the config is one of the following ... *) @@ -153,6 +158,7 @@ module Libvirtd_qemu = | nbd_entry | swtpm_entry | capability_filters_entry + | obsolete_entry let comment = [ label "#comment" . del /#[ \t]*/ "# " . store /([^ \t\n][^\n]*)?/ . del /\n/ "\n" ] let empty = [ label "#empty" . eol ] diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 7a056b037ed562fe5cdcae343084c914f72383a2..b6805ffc415da4e0380d63a3837dd6dd1dc21eb0 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -583,17 +583,6 @@ #bridge_helper = "/usr/libexec/qemu-bridge-helper" - -# If clear_emulator_capabilities is enabled, libvirt will drop all -# privileged capabilities of the QEMU/KVM emulator. This is enabled by -# default. -# -# Warning: Disabling this option means that a compromised guest can -# exploit the privileges and possibly do damage to the host. -# -#clear_emulator_capabilities = 1 - - # If enabled, libvirt will have QEMU set its process name to # "qemu:VM_NAME", where VM_NAME is the name of the VM. The QEMU # process will appear as "qemu:VM_NAME" in process listings and diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c index c24c99d1299a05d7c5a3a37d367a2490427c80df..389ac55beedba5c360142aa9a51853b9cc70cf55 100644 --- a/src/qemu/qemu_conf.c +++ b/src/qemu/qemu_conf.c @@ -234,8 +234,6 @@ virQEMUDriverConfigPtr virQEMUDriverConfigNew(bool privileged) cfg->prHelperName = g_strdup(QEMU_PR_HELPER); cfg->slirpHelperName = g_strdup(QEMU_SLIRP_HELPER); - cfg->clearEmulatorCapabilities = true; - cfg->securityDefaultConfined = true; cfg->securityRequireConfined = false; @@ -602,8 +600,6 @@ virQEMUDriverConfigLoadProcessEntry(virQEMUDriverConfigPtr cfg, } } - if (virConfGetValueBool(conf, "clear_emulator_capabilities", &cfg->clearEmulatorCapabilities) < 0) - return -1; if (virConfGetValueString(conf, "bridge_helper", &cfg->bridgeHelperName) < 0) return -1; diff --git a/src/qemu/qemu_conf.h b/src/qemu/qemu_conf.h index d2e0bd97e1317e4b23c70c1df11463e2e4856269..b9401635d7928733faa001bf194063c90457ed96 100644 --- a/src/qemu/qemu_conf.h +++ b/src/qemu/qemu_conf.h @@ -161,7 +161,6 @@ struct _virQEMUDriverConfig { bool relaxedACS; bool vncAllowHostAudio; bool nogfxAllowHostAudio; - bool clearEmulatorCapabilities; bool setProcessName; unsigned int maxProcesses; diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c index 27926c7670eb4389ae56954903dbf6d0b1a24183..5b82c22d96342863782bb60d8aacacf2f0ea0ad8 100644 --- a/src/qemu/qemu_domain.c +++ b/src/qemu/qemu_domain.c @@ -9512,8 +9512,7 @@ void qemuDomainObjCheckTaint(virQEMUDriverPtr driver, bool custom_hypervisor_feat = false; if (virQEMUDriverIsPrivileged(driver) && - (!cfg->clearEmulatorCapabilities || - cfg->user == 0 || + (cfg->user == 0 || cfg->group == 0)) qemuDomainObjTaint(driver, obj, VIR_DOMAIN_TAINT_HIGH_PRIVILEGES, logCtxt); diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c index 4b844b4b7c650962ea94b67073065737cc125f70..3e619ff7aa04ac806394dbec225bf65fc50383a4 100644 --- a/src/qemu/qemu_process.c +++ b/src/qemu/qemu_process.c @@ -6812,11 +6812,6 @@ qemuProcessLaunch(virConnectPtr conn, if (qemuDomainCreateNamespace(driver, vm) < 0) goto cleanup; - VIR_DEBUG("Clear emulator capabilities: %d", - cfg->clearEmulatorCapabilities); - if (cfg->clearEmulatorCapabilities) - virCommandClearCaps(cmd); - VIR_DEBUG("Setting up raw IO"); if (qemuProcessSetupRawIO(driver, vm, cmd) < 0) goto cleanup; diff --git a/src/qemu/test_libvirtd_qemu.aug.in b/src/qemu/test_libvirtd_qemu.aug.in index b9cf8d66881b3cfc12011915eaf5034587bf3763..dd90edf687a82dcf0f3088eb199e3821dd539521 100644 --- a/src/qemu/test_libvirtd_qemu.aug.in +++ b/src/qemu/test_libvirtd_qemu.aug.in @@ -72,7 +72,6 @@ module Test_libvirtd_qemu = { "auto_start_bypass_cache" = "0" } { "hugetlbfs_mount" = "/dev/hugepages" } { "bridge_helper" = "/usr/libexec/qemu-bridge-helper" } -{ "clear_emulator_capabilities" = "1" } { "set_process_name" = "1" } { "max_processes" = "0" } { "max_files" = "0" }