Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 01 Apr 2026 11:16:38 +0000
From:      Mark Johnston <markj@FreeBSD.org>
To:        src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org
Subject:   git: f3c772361f3b - main - vmm: Restore the ability to create VMs as root in a jail
Message-ID:  <69ccfe96.45285.612d5bc7@gitrepo.freebsd.org>

index | next in thread | raw e-mail

The branch main has been updated by markj:

URL: https://cgit.FreeBSD.org/src/commit/?id=f3c772361f3b6213ec7ae7de993b6953357c7b48

commit f3c772361f3b6213ec7ae7de993b6953357c7b48
Author:     Mark Johnston <markj@FreeBSD.org>
AuthorDate: 2026-04-01 09:25:27 +0000
Commit:     Mark Johnston <markj@FreeBSD.org>
CommitDate: 2026-04-01 11:16:14 +0000

    vmm: Restore the ability to create VMs as root in a jail
    
    The new PRIV_VMM_CREATE and DESTROY permissions should be allowed by
    jails, so need to be added to the list in prison_priv_check().  Then,
    modify vmmdev_create() to verify that the jail was created with the
    allow.vmm flag.  This is already verified when opening /dev/vmmctl, but
    checking again doesn't hurt and ensures that one can't pass the
    allow.vmm policy by passing a vmmctl fd along a unix domain socket from
    outside the jail.
    
    Rename vmm_priv_check() to vmm_jail_priv_check() to make the function's
    purpose more clear.
    
    Reported by:    novel
    Reviewed by:    bnovkov
    Fixes:          d4c05edd410e ("vmm: Add privilege checks to vmmctl operations")
    Differential Revision:  https://reviews.freebsd.org/D56119
---
 sys/dev/vmm/vmm_dev.c | 16 +++++++++++-----
 sys/kern/kern_jail.c  |  8 ++++++++
 2 files changed, 19 insertions(+), 5 deletions(-)

diff --git a/sys/dev/vmm/vmm_dev.c b/sys/dev/vmm/vmm_dev.c
index ed8e5b2e0777..a2775023838a 100644
--- a/sys/dev/vmm/vmm_dev.c
+++ b/sys/dev/vmm/vmm_dev.c
@@ -114,7 +114,7 @@ static int devmem_create_cdev(struct vmmdev_softc *sc, int id, char *devmem);
 static void vmmdev_destroy(struct vmmdev_softc *sc);
 
 static int
-vmm_priv_check(struct ucred *ucred)
+vmm_jail_priv_check(struct ucred *ucred)
 {
 	if (jailed(ucred) &&
 	    (ucred->cr_prison->pr_allow & pr_allow_vmm_flag) == 0)
@@ -371,7 +371,7 @@ vmmdev_open(struct cdev *dev, int flags, int fmt, struct thread *td)
 	 * A jail without vmm access shouldn't be able to access vmm device
 	 * files at all, but check here just to be thorough.
 	 */
-	error = vmm_priv_check(td->td_ucred);
+	error = vmm_jail_priv_check(td->td_ucred);
 	if (error != 0)
 		return (error);
 
@@ -940,7 +940,7 @@ sysctl_vmm_destroy(SYSCTL_HANDLER_ARGS)
 	char *buf;
 	int error, buflen;
 
-	error = vmm_priv_check(req->td->td_ucred);
+	error = vmm_jail_priv_check(req->td->td_ucred);
 	if (error)
 		return (error);
 
@@ -1016,6 +1016,12 @@ vmmdev_create(const char *name, uint32_t flags, struct ucred *cred)
 		    "An unprivileged user must run VMs in monitor mode"));
 	}
 
+	if ((error = vmm_jail_priv_check(cred)) != 0) {
+		sx_xunlock(&vmmdev_mtx);
+		return (EXTERROR(error,
+		    "VMs cannot be created in the current jail"));
+	}
+
 	if (!chgvmmcnt(cred->cr_ruidinfo, 1, vm_maxvmms)) {
 		sx_xunlock(&vmmdev_mtx);
 		return (ENOMEM);
@@ -1061,7 +1067,7 @@ sysctl_vmm_create(SYSCTL_HANDLER_ARGS)
 	if (!vmm_initialized)
 		return (ENXIO);
 
-	error = vmm_priv_check(req->td->td_ucred);
+	error = vmm_jail_priv_check(req->td->td_ucred);
 	if (error != 0)
 		return (error);
 
@@ -1126,7 +1132,7 @@ vmmctl_open(struct cdev *cdev, int flags, int fmt, struct thread *td)
 	int error;
 	struct vmmctl_priv *priv;
 
-	error = vmm_priv_check(td->td_ucred);
+	error = vmm_jail_priv_check(td->td_ucred);
 	if (error != 0)
 		return (error);
 
diff --git a/sys/kern/kern_jail.c b/sys/kern/kern_jail.c
index 9f78cb42aeb1..384825b7f8ac 100644
--- a/sys/kern/kern_jail.c
+++ b/sys/kern/kern_jail.c
@@ -4736,6 +4736,14 @@ prison_priv_check(struct ucred *cred, int priv)
 		else
 			return (EPERM);
 
+	case PRIV_VMM_CREATE:
+	case PRIV_VMM_DESTROY:
+		/*
+		 * Jailed root can create and destroy VMs; the vmm module
+		 * additionally checks for the allow.vmm flag.
+		 */
+		return (0);
+
 	case PRIV_VMM_PPTDEV:
 		/*
 		 * Allow jailed root to manage passthrough devices.  vmm(4) also


home | help

Want to link to this message? Use this
URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?69ccfe96.45285.612d5bc7>