<feed xmlns='http://www.w3.org/2005/Atom'>
<title>procd/jail, branch master</title>
<subtitle>OpenWrt service / process manager</subtitle>
<id>https://git-03.infra.openwrt.org/project/procd/atom?h=master</id>
<link rel='self' href='https://git-03.infra.openwrt.org/project/procd/atom?h=master'/>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/'/>
<updated>2026-11-03T11:39:51Z</updated>
<entry>
<title>service: add workdir support for daemon instances</title>
<updated>2026-11-03T11:39:51Z</updated>
<author>
<name>Tianling Shen</name>
</author>
<published>2026-10-03T06:24:53Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=2e013572e8b3a33c61960f1e1c032dde52f5a78d'/>
<id>urn:sha1:2e013572e8b3a33c61960f1e1c032dde52f5a78d</id>
<content type='text'>
Allow instances to select a working directory with the workdir option.
Change directory after setting the process identity and fail startup
if the directory cannot be entered. Preserve the existing behavior
when workdir is omitted.

Pass the directory to ujail through a new -B option, reusing its
existing directory switch after jail setup. Track workdir changes,
include the value in instance dumps, and release owned strings.

For OCI bundle instances, process.cwd from the bundle takes precedence
over workdir because the bundle is parsed after the command-line options.

Signed-off-by: Tianling Shen &lt;cnsztl@immortalwrt.org&gt;
</content>
</entry>
<entry>
<title>jail: fix typo in usage output</title>
<updated>2026-11-02T15:59:26Z</updated>
<author>
<name>Daniel Golle</name>
</author>
<published>2026-11-02T14:50:51Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=fea76294a68196c633cd2f323a6958f8c0d25648'/>
<id>urn:sha1:fea76294a68196c633cd2f323a6958f8c0d25648</id>
<content type='text'>
'remont' should be 'remount'.

Fixes: a4505284b4d2 ("jail: reworks &amp; cleanups")
Signed-off-by: Daniel Golle &lt;daniel@makrotopia.org&gt;
</content>
</entry>
<entry>
<title>jail: share the live resolv.conf with host-network jails</title>
<updated>2026-11-02T15:59:26Z</updated>
<author>
<name>Daniel Golle</name>
</author>
<published>2026-11-01T15:30:24Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=3f61bf11b41aecea6bba4d018bcfda96c314479d'/>
<id>urn:sha1:3f61bf11b41aecea6bba4d018bcfda96c314479d</id>
<content type='text'>
A jail without its own network namespace gets the host's
/etc/resolv.conf bind-mounted, which pins the inode the symlink chain
resolves to at start, /tmp/resolv.conf.d/resolv.conf.auto. netifd
replaces that file by rename, so a jail started before the uplink had
DNS keeps the empty boot-time file for good, and a jailed sysntpd never
resolves its servers.

Bind /tmp/resolv.conf.d read-only to /dev/resolv.conf.d in such jails
and make /etc/resolv.conf a relative symlink into it, set up as for
containers with a private netifd. The mount point lives in the /dev
ujail builds itself, so read-only and overlay roots work alike. The
link targets resolv.conf in that directory when present, else the
host's resolved path when it lies there. Otherwise, or when the bundle
mounts /etc/resolv.conf itself, the file bind stays.

Fixes: 77a6782d6e4e ("jail: mount-bind /etc/resolv.conf for non-netns jails")
Signed-off-by: Daniel Golle &lt;daniel@makrotopia.org&gt;
</content>
</entry>
<entry>
<title>jail: warn when the jailed process can undo read-only mounts</title>
<updated>2026-11-01T20:16:38Z</updated>
<author>
<name>Daniel Golle</name>
</author>
<published>2026-11-01T18:23:53Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=0d7cd8005e9c1ee1791380571f46b09d65a430ac'/>
<id>urn:sha1:0d7cd8005e9c1ee1791380571f46b09d65a430ac</id>
<content type='text'>
Mount flags alone do not keep a jail's read-only mounts read-only: a
process that holds CAP_SYS_ADMIN in the jail's user namespace can
remount them read-write, unmount them or mount over them, and the
kernel locks the flags only of mounts inherited from a more privileged
namespace, which ujail's own mounts are not. Jailed services prevent
this by dropping CAP_SYS_ADMIN or by a seccomp filter that denies the
mount syscalls; nothing tells when a jail has neither.

The child decides with prctl() alone, after the capability and identity
changes and before exec, whether CAP_SYS_ADMIN survives the exec: it
is ambient, or the process runs as uid 0 without SECBIT_NOROOT and the
bounding set still holds it. The parent logs a warning when that is
the case and no enforcing seccomp filter denies every syscall of the
mount family on all paths. seccomp_nr_allows() gains the "allowed on
some path" mode this needs; anything it cannot follow counts as
allowed there, as do log, trace and user-notification returns.

Signed-off-by: Daniel Golle &lt;daniel@makrotopia.org&gt;
</content>
</entry>
<entry>
<title>jail: do not lock SECBIT_KEEP_CAPS</title>
<updated>2026-11-01T20:00:24Z</updated>
<author>
<name>Daniel Golle</name>
</author>
<published>2026-11-01T19:21:24Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=0d3c5dc1bb56cc4908f217daaa4ab8aee9663979'/>
<id>urn:sha1:0d3c5dc1bb56cc4908f217daaa4ab8aee9663979</id>
<content type='text'>
With a capability set to apply, ujail locks SECBIT_KEEP_CAPS off before
the exec. prctl(PR_SET_KEEPCAPS) then fails with EPERM, so a service
that drops to its own user and keeps part of its capabilities across
setuid(), as dnsmasq does, cannot start under a capabilities file
("setting capabilities failed: Operation not permitted").

Leave the bit unlocked. It only lets a process keep capabilities it
already holds, within the bounding set, and execve() clears it. The OCI
runtime specification does not mention securebits, and runc and crun
set and clear PR_SET_KEEPCAPS themselves without locking it.

Fixes: acf36f2777ae ("jail: seteuid before clone(CLONE_NEWUSER)")
Signed-off-by: Daniel Golle &lt;daniel@makrotopia.org&gt;
</content>
</entry>
<entry>
<title>jail: fs: apply the mount flags to path bind clones</title>
<updated>2026-11-01T17:43:55Z</updated>
<author>
<name>Daniel Golle</name>
</author>
<published>2026-11-01T17:43:55Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=8010a5ff7f1c5637b37d15145fa667f317ae070a'/>
<id>urn:sha1:8010a5ff7f1c5637b37d15145fa667f317ae070a</id>
<content type='text'>
add_2paths_and_deps() and add_2paths_nodeps() clone each bind source
with open_tree() in the parent, and mount_one() moves such a clone into
the jail with do_mount_fd(), which never applies the mount's flags. The
clone keeps the flags of the host mount it was taken from, so every
-r, -b and non-idmapped -k path, the jailed program and its ELF
interpreter are writable from inside the jail when the host mount is,
e.g. the overlay root or /tmp: a jailed uid 0 process can rewrite a
staged host file such as /etc/hosts.

Set the mount's flags on the detached clone with mount_setattr() right
after open_tree(), while still running as real root. Should that fail
the clone is dropped and do_mount() binds by path and remounts the
target with the requested flags.

Fixes: 0d1c1d45a1fa ("jail: provision per-instance files via idmapped credential binds")
Signed-off-by: Daniel Golle &lt;daniel@makrotopia.org&gt;
</content>
</entry>
<entry>
<title>jail: seccomp: skip a mapped path that does not fit</title>
<updated>2026-10-25T08:47:02Z</updated>
<author>
<name>Felix Fietkau</name>
</author>
<published>2026-10-25T08:47:02Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=2bf9d39e4a59887625b58f3ee9dad0c135f10cd1'/>
<id>urn:sha1:2bf9d39e4a59887625b58f3ee9dad0c135f10cd1</id>
<content type='text'>
find_libc_init() builds /proc/&lt;pid&gt;/root&lt;path&gt; for each mapped file
with an unchecked snprintf(). gcc 14 cannot bound the length of the
entry in seen[] and warns, and -Werror turns that into a build failure
where _FORTIFY_SOURCE is not set:

  jail/seccomp-inject.c:1201:64: error: '%s' directive output may be
  truncated writing up to 12287 bytes into a region of size between
  4138 and 4148 [-Werror=format-truncation=]

Skip a mapped file whose rooted path does not fit, so that no symbol
is looked up in a truncated path.

Fixes: f15d0c407c09 ("jail: apply OCI seccomp filters via ptrace syscall injection")
Signed-off-by: Felix Fietkau &lt;nbd@nbd.name&gt;
</content>
</entry>
<entry>
<title>jail: fail a too long resolv.conf path for a private netifd</title>
<updated>2026-10-25T08:43:34Z</updated>
<author>
<name>Felix Fietkau</name>
</author>
<published>2026-10-24T05:20:20Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=b0788bab97c493f3fd457955b7831ed2b3ada0e3'/>
<id>urn:sha1:b0788bab97c493f3fd457955b7831ed2b3ada0e3</id>
<content type='text'>
The host side of a private netifd jail builds /tmp/resolv.conf-&lt;name&gt;.d
and its resolv.conf.auto with unchecked snprintf() calls. A long jail
name truncates both paths, so ujail creates and binds a directory with
another name. gcc 14 also warns at the second call, and the -Werror of
CMakeLists.txt turns that into a build failure wherever _FORTIFY_SOURCE
is not set, for example with a host gcc:

  jail/jail.c:7490:75: error: '/resolv.conf.auto' directive output may
  be truncated writing 17 bytes into a region of size between 1 and
  4096 [-Werror=format-truncation=]

Fail the jail when either path does not fit, as for a failed mkdir() of
the directory.

Fixes: 24495d92cc4f ("jail: provide resolv.conf to containers with a private netifd")
Signed-off-by: Felix Fietkau &lt;nbd@nbd.name&gt;
</content>
</entry>
<entry>
<title>jail: fs: terminate the script interpreter path</title>
<updated>2026-10-25T08:43:34Z</updated>
<author>
<name>Felix Fietkau</name>
</author>
<published>2026-07-04T20:00:24Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=c58a8da96c2ca1677f73da85ccf7523fc8b2ee22'/>
<id>urn:sha1:c58a8da96c2ca1677f73da85ccf7523fc8b2ee22</id>
<content type='text'>
add_script_interp() copies the interpreter path from the shebang line
with strncpy() without terminating the destination, so
add_path_and_deps() operates on the path followed by uninitialised
stack bytes. Depending on the stack contents the interpreter of a
staged script is then not found and its dependencies are not mounted
into the jail.

Terminate the buffer and reject interpreter paths that no longer fit
including the terminator.

Fixes: 9211278a18da ("ujail: automatically add script (#!) interpreter")
Signed-off-by: Felix Fietkau &lt;nbd@nbd.name&gt;
</content>
</entry>
<entry>
<title>jail: cgroups: avoid truncating the cpu.max value</title>
<updated>2026-10-25T08:43:34Z</updated>
<author>
<name>Felix Fietkau</name>
</author>
<published>2026-07-04T19:59:50Z</published>
<link rel='alternate' type='text/html' href='https://git-03.infra.openwrt.org/project/procd/commit/?id=2cf29849d8729808494c2f2fdd4fe3df5687d7c8'/>
<id>urn:sha1:2cf29849d8729808494c2f2fdd4fe3df5687d7c8</id>
<content type='text'>
The buffer that holds the converted cpu.max value is 32 bytes. Quota and
period are 64-bit values, and together they can need 40 characters plus
the terminator. snprintf() then truncates the value and nothing reports
the error, so cgroups_set() writes a wrong limit. Enlarge the buffer.

Fixes: 16159bb1f70f ("jail: parse OCI cgroups resources")
Signed-off-by: Felix Fietkau &lt;nbd@nbd.name&gt;
</content>
</entry>
</feed>
