jail: Add exec.prepare and exec.release command hooks

This change introduces new jail command hooks that run before and after any
other actions.

The exec.prepare hook can be used for example to invoke a script that checks
if the jail's root exists, creating it if it does not. Since arbitrary
variables in jail.conf can be passed to the command, it can be pretty useful
for templating jails.

An example use case for exec.release would be to remove the filesystem of an
ephemeral jail.

The names "prepare" and "release" are borrowed from the names of similar hooks
in libvirt.

Reviewed by:	jamie, manpages, mmacy
Approved by:	mmacy (mentor)
MFC after:	1 week
Differential Revision:	https://reviews.freebsd.org/D24829
This commit is contained in:
Ryan Moeller 2020-05-14 23:38:11 +00:00
parent 1d2e31af14
commit 66005c453d
5 changed files with 19 additions and 2 deletions

View File

@ -148,7 +148,8 @@ next_command(struct cfjail *j)
if (j->comstring == NULL || j->comstring->len == 0 ||
(create_failed && (comparam == IP_EXEC_PRESTART ||
comparam == IP_EXEC_CREATED || comparam == IP_EXEC_START ||
comparam == IP_COMMAND || comparam == IP_EXEC_POSTSTART)))
comparam == IP_COMMAND || comparam == IP_EXEC_POSTSTART ||
comparam == IP_EXEC_PREPARE)))
continue;
switch (run_command(j)) {
case -1:

View File

@ -71,8 +71,10 @@ static const struct ipspec intparams[] = {
[IP_EXEC_JAIL_USER] = {"exec.jail_user", PF_INTERNAL},
[IP_EXEC_POSTSTART] = {"exec.poststart", PF_INTERNAL},
[IP_EXEC_POSTSTOP] = {"exec.poststop", PF_INTERNAL},
[IP_EXEC_PREPARE] = {"exec.prepare", PF_INTERNAL},
[IP_EXEC_PRESTART] = {"exec.prestart", PF_INTERNAL},
[IP_EXEC_PRESTOP] = {"exec.prestop", PF_INTERNAL},
[IP_EXEC_RELEASE] = {"exec.release", PF_INTERNAL},
[IP_EXEC_CREATED] = {"exec.created", PF_INTERNAL},
[IP_EXEC_START] = {"exec.start", PF_INTERNAL},
[IP_EXEC_STOP] = {"exec.stop", PF_INTERNAL},

View File

@ -25,7 +25,7 @@
.\"
.\" $FreeBSD$
.\"
.Dd April 17, 2020
.Dd May 14, 2020
.Dt JAIL 8
.Os
.Sh NAME
@ -726,6 +726,11 @@ not be created or removed, as appropriate.
.Pp
The pseudo-parameters are:
.Bl -tag -width indent
.It Va exec.prepare
Command(s) to run in the system environment to prepare a jail for creation.
These commands are executed before assigning IP addresses and mounting
filesystems, so they may be used to create a new jail filesystem if it does
not already exist.
.It Va exec.prestart
Command(s) to run in the system environment before a jail is created.
.It Va exec.created
@ -760,6 +765,11 @@ A typical command to run is
.Dq sh /etc/rc.shutdown jail .
.It Va exec.poststop
Command(s) to run in the system environment after a jail is removed.
.It Va exec.release
Command(s) to run in the system environment after all other actions are done.
These commands are executed after unmounting filesystems and removing IP
addresses, so they may be used to remove a jail filesystem if it is no longer
needed.
.It Va exec.clean
Run commands in a clean environment.
The environment is discarded except for

View File

@ -87,6 +87,7 @@ static struct permspec perm_sysctl[] = {
static const enum intparam startcommands[] = {
IP__NULL,
IP_EXEC_PREPARE,
#ifdef INET
IP__IP4_IFADDR,
#endif
@ -126,6 +127,7 @@ static const enum intparam stopcommands[] = {
#ifdef INET
IP__IP4_IFADDR,
#endif
IP_EXEC_RELEASE,
IP__NULL
};

View File

@ -87,8 +87,10 @@ enum intparam {
IP_EXEC_JAIL_USER, /* Run jailed commands as this user */
IP_EXEC_POSTSTART, /* Commands run outside jail after creating */
IP_EXEC_POSTSTOP, /* Commands run outside jail after removing */
IP_EXEC_PREPARE, /* Commands run outside jail before addrs and mounting */
IP_EXEC_PRESTART, /* Commands run outside jail before creating */
IP_EXEC_PRESTOP, /* Commands run outside jail before removing */
IP_EXEC_RELEASE, /* Commands run outside jail after addrs and unmounted */
IP_EXEC_CREATED, /* Commands run outside jail right after it was started */
IP_EXEC_START, /* Commands run inside jail on creation */
IP_EXEC_STOP, /* Commands run inside jail on removal */