qemuSecurityCommandRun() causes an explicit domain transition of the new process, but passt ships with its own SELinux policy, with external interfaces for libvirtd, so we simply need to transition from virtd_t to passt_t as passt is executed. The qemu type enforcement rules have little to do with it. That is, if we switch to svirt_t, passt will run in the security context that's intended for QEMU, which allows a number of operations not needed by passt. On the other hand, with a switch to svirt_t, passt won't be able to create its own PID file. Usage of those new interfaces is implemented by this change in selinux-policy: https://github.com/fedora-selinux/selinux-policy/pull/1613 Replace qemuSecurityCommandRun() with virCommandRun(), and explicitly set the label, preserving the correct MCS range for the given VM instance. This is a temporary measure: eventually, we'll need a more generic and elegant mechanism for helper binaries. Fixes: a56f0168d576 ("qemu: hook up passt config to qemu domains") Signed-off-by: Stefano Brivio <sbrivio@xxxxxxxxxx> --- src/qemu/qemu_passt.c | 33 +++++++++++++++++++++++++++------ 1 file changed, 27 insertions(+), 6 deletions(-) diff --git a/src/qemu/qemu_passt.c b/src/qemu/qemu_passt.c index 1217a6a087..81f48dd630 100644 --- a/src/qemu/qemu_passt.c +++ b/src/qemu/qemu_passt.c @@ -30,6 +30,11 @@ #include "virlog.h" #include "virpidfile.h" +#ifdef WITH_SELINUX +# include <selinux/selinux.h> +# include <selinux/context.h> +#endif + #define VIR_FROM_THIS VIR_FROM_NONE VIR_LOG_INIT("qemu.passt"); @@ -158,8 +163,11 @@ qemuPasstStart(virDomainObj *vm, g_autofree char *errbuf = NULL; char macaddr[VIR_MAC_STRING_BUFLEN]; size_t i; - int exitstatus = 0; - int cmdret = 0; +#ifdef WITH_SELINUX + virSecurityLabelDef *seclabel; + context_t s; + const char *newLabel; +#endif cmd = virCommandNew(PASST); @@ -271,18 +279,31 @@ qemuPasstStart(virDomainObj *vm, if (qemuExtDeviceLogCommand(driver, vm, cmd, "passt") < 0) return -1; - if (qemuSecurityCommandRun(driver, vm, cmd, -1, -1, &exitstatus, &cmdret) < 0) - goto error; +#ifdef WITH_SELINUX + /* TODO: Implement a new security manager function for helper binaries, + * possibly deriving domain names from security attributes of the helper + * binary itself. + */ + seclabel = virDomainDefGetSecurityLabelDef(vm->def, "selinux"); + s = context_new(seclabel->label); + context_type_set(s, "passt_t"); + newLabel = context_str(s); + + virCommandSetSELinuxLabel(cmd, newLabel); +#endif - if (cmdret < 0 || exitstatus != 0) { + if (virCommandRun(cmd, NULL)) { virReportError(VIR_ERR_INTERNAL_ERROR, _("Could not start 'passt': %s"), NULLSTR(errbuf)); goto error; } + context_free(s); + return 0; error: - qemuPasstKill(pidfile); + context_free(s); + qemuPasstKill(pidfile, passtSocketName); return -1; } -- 2.39.1