Skip to content

Commit

Permalink
confd: major behavior change, run container --read-only always
Browse files Browse the repository at this point in the history
Container support in Infix was released with v24.02, so this change may
unfortunately break a few use-cases out there.  Regrettable as this is,
the default behavior, including how containers are started after boot,
break other use-cases that were considered more important.

As of this commit:

 - all containers in Infix run in read-only mode, use volumes and
   mounts for persistence across reboot/stop/start/upgrade
 - all containers are now "recreated" at boot or related config changes,
   this ensures an OCI image embedded in the Infix image, /lib/oci/, is
   always used as the base for a running container

Fixes #823

Signed-off-by: Joachim Wiberg <troglobit@gmail.com>
  • Loading branch information
troglobit committed Nov 20, 2024
1 parent db44771 commit 1347080
Show file tree
Hide file tree
Showing 6 changed files with 28 additions and 45 deletions.
13 changes: 4 additions & 9 deletions board/common/rootfs/usr/sbin/container
Original file line number Diff line number Diff line change
Expand Up @@ -108,9 +108,9 @@ create()
logging="--log-driver k8s-file --log-opt path=/run/containers/$name.fifo"
fi

args="$args --replace --quiet --cgroup-parent=containers $caps"
args="$args --read-only --replace --quiet --cgroup-parent=containers $caps"
args="$args --restart=$restart --systemd=false --tz=local $privileged"
args="$args $ro $vol $mount $hostname $entrypoint $env $port $logging"
args="$args $vol $mount $hostname $entrypoint $env $port $logging"
pidfn=/run/container:${name}.pid

[ -n "$quiet" ] || log "---------------------------------------"
Expand All @@ -136,8 +136,7 @@ create()
# shellcheck disable=SC2048
log "Calling podman create --name $name --conmon-pidfile=$pidfn $args $image $*"
if podman create --name "$name" --conmon-pidfile="$pidfn" $args "$image" $*; then
[ -n "$quiet" ] || log "Successfully created container $name from $image"
rm -f "/run/containers/env/${name}.env"
[ -n "$quiet" ] || log "Successfully created container $name from $image"
[ -n "$manual" ] || start "$name"
exit 0
fi
Expand Down Expand Up @@ -267,7 +266,6 @@ options:
Syntax: [[ip:][hostPort]:]containerPort[/protocol]
-q, --quiet Quiet operation, called from confd
-r, --restart POLICY One of "no", "always", or "on-failure:NUM"
--read-only Do not create a writable layer
-s, --simple Show output in simplified format
-v, --volume NAME:PATH Create named volume mounted inside container on PATH
Expand Down Expand Up @@ -386,9 +384,6 @@ while [ "$1" != "" ]; do
shift
restart=$1
;;
--read-only)
ro="--read-only=true"
;;
-s | --simple)
simple=true
;;
Expand Down Expand Up @@ -627,7 +622,7 @@ case $cmd in
;;
upgrade)
# Start script used to initially create container
script=/var/lib/containers/active/S01-${1}.sh
script=/run/containers/active/S01-${1}.sh

# Find container image
img=$(podman inspect "$1" | jq -r .[].ImageName)
Expand Down
2 changes: 1 addition & 1 deletion package/execd/execd.conf
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
service log:prio:local1.err,tag:container \
[2345] execd /run/containers/queue /var/lib/containers/active -- Container job runner
[2345] execd /run/containers/queue /run/containers/active -- Container job runner
2 changes: 1 addition & 1 deletion package/execd/tmpfiles.conf
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
d /run/containers/args 0700 - -
d /run/containers/files 0700 - -
d /var/lib/containers/active 0700 - -
d /var/lib/containers/oci 0755 - -
d /run/containers/inbox 0700 - -
d /run/containers/queue 0700 - -
d /run/containers/active 0700 - -
d /run/cni 0755 - -
L+ /var/lib/cni - - - - /run/cni
50 changes: 16 additions & 34 deletions src/confd/src/infix-containers.c
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
#define CFG_XPATH "/infix-containers:containers"
#define INBOX_QUEUE "/run/containers/inbox"
#define JOB_QUEUE "/run/containers/queue"
#define ACTIVE_QUEUE "/var/lib/containers/active"
#define ACTIVE_QUEUE "/run/containers/active"
#define LOGGER "logger -t container -p local1.notice"


Expand Down Expand Up @@ -56,9 +56,6 @@ static int add(const char *name, struct lyd_node *cif)
fprintf(fp, " --hostname %s", buf);
}

if (lydx_is_enabled(cif, "read-only"))
fprintf(fp, " --read-only");

if (lydx_is_enabled(cif, "privileged"))
fprintf(fp, " --privileged");

Expand Down Expand Up @@ -392,15 +389,7 @@ static void cleanup(sr_session_ctx_t *session, struct confd *confd)
/*
* Containers depend on a lot of other system resources being properly
* set up, e.g., networking, which is run by dagger. So we need to wait
* for all that before we can launch new, or modified, containers. The
* latter is the tricky part.
*
* By default, containers get a writable layer which is preserved across
* restarts/reboots of container or host -- provided we don't recreate
* them on a reboot. Hence the cmp magic below: we check if the command
* to create a container is the same as what is already activated, if it
* is already activated we know 'podman create' has done its thing and
* we can safely start the container.
* for all that before we can launch new, or modified, containers.
*/
void infix_containers_post_hook(sr_session_ctx_t *session, struct confd *confd)
{
Expand All @@ -416,33 +405,26 @@ void infix_containers_post_hook(sr_session_ctx_t *session, struct confd *confd)
}

while ((d = readdir(dir))) {
char curr[strlen(ACTIVE_QUEUE) + strlen(d->d_name) + 2];
char next[strlen(INBOX_QUEUE) + strlen(d->d_name) + 2];
char name[strlen(d->d_name) + 1];
char *ptr;

if (d->d_name[0] == '.')
continue;

snprintf(curr, sizeof(curr), "%s/%s", ACTIVE_QUEUE, d->d_name);
snprintf(next, sizeof(next), "%s/%s", INBOX_QUEUE, d->d_name);
if (!systemf("cmp %s %s >/dev/null 2>&1", curr, next)) {
char name[strlen(d->d_name) + 1];
char *ptr;

strlcpy(name, d->d_name, sizeof(name));
ptr = strstr(name, ".sh");
if (ptr) {
char *nm = NULL;

*ptr = 0;
if (!strncmp(name, "S01-", 4))
nm = &name[4];

/* New job is already active, no changes, skipping ... */
if (nm && !is_manual(session, nm))
systemf("initctl -bnq cond set container:%s", nm);
}
remove(next);
continue;

strlcpy(name, d->d_name, sizeof(name));
ptr = strstr(name, ".sh");
if (ptr) {
char *nm = NULL;

*ptr = 0;
if (!strncmp(name, "S01-", 4))
nm = &name[4];

if (nm && !is_manual(session, nm))
systemf("initctl -bnq cond set container:%s", nm);
}

if (movefile(next, JOB_QUEUE))
Expand Down
6 changes: 6 additions & 0 deletions src/confd/yang/infix-containers.yang
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,11 @@ module infix-containers {
prefix infix-sys;
}

revision 2024-11-12 {
description "Deprecate read-only, it is now always true.";
reference "internal";
}

revision 2024-10-14 {
description "Two major changes:
- Allow changing name of host interfaces inside container
Expand Down Expand Up @@ -256,6 +261,7 @@ module infix-containers {
}

leaf read-only {
status deprecated; // This is now the default, setting kept only to not break configs
description "Create a read-only container. Use volumes for writable directories.";
type boolean;
}
Expand Down

0 comments on commit 1347080

Please sign in to comment.