aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorOphestra <cat@gensokyo.uk>2025-08-01 21:23:52 +0900
committerOphestra <cat@gensokyo.uk>2025-08-01 21:23:52 +0900
commitaf0899de9640b4336050b07b739818fdc3add08b (patch)
treedfc84b596e4d256b929ca91978c40db5eca5bdc4
parent547a2adaa488556f0504e186c5c1dfb0e679c935 (diff)
hst/container: mount tmpfs via magic src string
There's often good reason to mount tmpfs in the container. Signed-off-by: Ophestra <cat@gensokyo.uk>
-rw-r--r--hst/container.go14
-rw-r--r--internal/app/app_pd_linux_test.go8
-rw-r--r--internal/app/container_linux.go14
-rw-r--r--internal/app/seal_linux.go11
-rw-r--r--test/sandbox/case/pd.nix2
5 files changed, 39 insertions, 10 deletions
diff --git a/hst/container.go b/hst/container.go
index 56229929..9ca14a8b 100644
--- a/hst/container.go
+++ b/hst/container.go
@@ -6,6 +6,20 @@ import (
"hakurei.app/container/seccomp"
)
+const (
+ // SourceTmpfs causes tmpfs to be mounted on [FilesystemConfig.Dst]
+ // when assigned to [FilesystemConfig.Src].
+ SourceTmpfs = "tmpfs"
+
+ // TmpfsPerm is the permission bits for tmpfs mount points
+ // configured through [FilesystemConfig].
+ TmpfsPerm = 0755
+
+ // TmpfsSize is the size for tmpfs mount points
+ // configured through [FilesystemConfig].
+ TmpfsSize = 0
+)
+
type (
// ContainerConfig describes the container configuration baseline to which the app implementation adds upon.
ContainerConfig struct {
diff --git a/internal/app/app_pd_linux_test.go b/internal/app/app_pd_linux_test.go
index aea59d1c..7f0049bf 100644
--- a/internal/app/app_pd_linux_test.go
+++ b/internal/app/app_pd_linux_test.go
@@ -47,6 +47,7 @@ var testCasesPd = []sealTestCase{
Tmpfs(hst.Tmp, 4096, 0755).
Dev("/dev").Mqueue("/dev/mqueue").
Bind("/dev/kvm", "/dev/kvm", container.BindWritable|container.BindDevice|container.BindOptional).
+ Readonly("/var/run/nscd", 0755).
Tmpfs("/run/user/1971", 8192, 0755).
Tmpfs("/run/dbus", 8192, 0755).
Etc("/etc", "4a450b6596d7bc15bd01780eb9a607ac").
@@ -55,8 +56,7 @@ var testCasesPd = []sealTestCase{
Bind("/tmp/hakurei.1971/tmpdir/0", "/tmp", container.BindWritable).
Bind("/home/chronos", "/home/chronos", container.BindWritable).
Place("/etc/passwd", []byte("chronos:x:65534:65534:Hakurei:/home/chronos:/run/current-system/sw/bin/zsh\n")).
- Place("/etc/group", []byte("hakurei:x:65534:\n")).
- Tmpfs("/var/run/nscd", 8192, 0755),
+ Place("/etc/group", []byte("hakurei:x:65534:\n")),
SeccompPresets: seccomp.PresetExt | seccomp.PresetDenyDevel,
HostNet: true,
RetainSession: true,
@@ -181,6 +181,7 @@ var testCasesPd = []sealTestCase{
Dev("/dev").Mqueue("/dev/mqueue").
Bind("/dev/dri", "/dev/dri", container.BindWritable|container.BindDevice|container.BindOptional).
Bind("/dev/kvm", "/dev/kvm", container.BindWritable|container.BindDevice|container.BindOptional).
+ Readonly("/var/run/nscd", 0755).
Tmpfs("/run/user/1971", 8192, 0755).
Tmpfs("/run/dbus", 8192, 0755).
Etc("/etc", "ebf083d1b175911782d413369b64ce7c").
@@ -194,8 +195,7 @@ var testCasesPd = []sealTestCase{
Bind("/run/user/1971/hakurei/ebf083d1b175911782d413369b64ce7c/pulse", "/run/user/65534/pulse/native", 0).
Place(hst.Tmp+"/pulse-cookie", nil).
Bind("/tmp/hakurei.1971/ebf083d1b175911782d413369b64ce7c/bus", "/run/user/65534/bus", 0).
- Bind("/tmp/hakurei.1971/ebf083d1b175911782d413369b64ce7c/system_bus_socket", "/run/dbus/system_bus_socket", 0).
- Tmpfs("/var/run/nscd", 8192, 0755),
+ Bind("/tmp/hakurei.1971/ebf083d1b175911782d413369b64ce7c/system_bus_socket", "/run/dbus/system_bus_socket", 0),
SeccompPresets: seccomp.PresetExt | seccomp.PresetDenyDevel,
HostNet: true,
RetainSession: true,
diff --git a/internal/app/container_linux.go b/internal/app/container_linux.go
index cd9448a8..09909d83 100644
--- a/internal/app/container_linux.go
+++ b/internal/app/container_linux.go
@@ -156,6 +156,20 @@ func newContainer(s *hst.ContainerConfig, os sys.State, prefix string, uid, gid
continue
}
+ // special filesystems
+ switch c.Src {
+ case hst.SourceTmpfs:
+ if !path.IsAbs(c.Dst) {
+ return nil, nil, fmt.Errorf("tmpfs dst %q is not absolute", c.Dst)
+ }
+ if c.Write {
+ params.Tmpfs(c.Dst, hst.TmpfsSize, hst.TmpfsPerm)
+ } else {
+ params.Readonly(c.Dst, hst.TmpfsPerm)
+ }
+ continue
+ }
+
if !path.IsAbs(c.Src) {
return nil, nil, fmt.Errorf("src path %q is not absolute", c.Src)
}
diff --git a/internal/app/seal_linux.go b/internal/app/seal_linux.go
index d020697e..cc92db29 100644
--- a/internal/app/seal_linux.go
+++ b/internal/app/seal_linux.go
@@ -246,11 +246,6 @@ func (seal *outcome) finalise(ctx context.Context, sys sys.State, config *hst.Co
RootFlags: container.BindWritable,
}
- // hide nscd from sandbox if present
- nscd := "/var/run/nscd"
- if _, err := sys.Stat(nscd); !errors.Is(err, fs.ErrNotExist) {
- conf.Cover = append(conf.Cover, nscd)
- }
// bind GPU stuff
if config.Enablements&(system.EX11|system.EWayland) != 0 {
conf.Filesystem = append(conf.Filesystem, &hst.FilesystemConfig{Src: "/dev/dri", Device: true})
@@ -258,6 +253,12 @@ func (seal *outcome) finalise(ctx context.Context, sys sys.State, config *hst.Co
// opportunistically bind kvm
conf.Filesystem = append(conf.Filesystem, &hst.FilesystemConfig{Src: "/dev/kvm", Device: true})
+ // hide nscd from container if present
+ const nscd = "/var/run/nscd"
+ if _, err := sys.Stat(nscd); !errors.Is(err, fs.ErrNotExist) {
+ conf.Filesystem = append(conf.Filesystem, &hst.FilesystemConfig{Dst: nscd, Src: hst.SourceTmpfs})
+ }
+
config.Container = conf
}
diff --git a/test/sandbox/case/pd.nix b/test/sandbox/case/pd.nix
index 569e325a..950afdfe 100644
--- a/test/sandbox/case/pd.nix
+++ b/test/sandbox/case/pd.nix
@@ -181,6 +181,7 @@
(ent ignore "/dev/console" "rw,nosuid,noexec,relatime" "devpts" "devpts" "rw,gid=3,mode=620,ptmxmode=666")
(ent "/" "/dev/mqueue" "rw,nosuid,nodev,noexec,relatime" "mqueue" "mqueue" "rw")
(ent "/kvm" "/dev/kvm" "rw,nosuid" "devtmpfs" "devtmpfs" ignore)
+ (ent "/" "/run/nscd" "ro,nosuid,nodev,relatime" "tmpfs" "readonly" "ro,mode=755,uid=1000000,gid=1000000")
(ent "/" "/run/user/1000" "rw,nosuid,nodev,relatime" "tmpfs" "ephemeral" "rw,size=8k,mode=755,uid=1000000,gid=1000000")
(ent "/" "/run/dbus" "rw,nosuid,nodev,relatime" "tmpfs" "ephemeral" "rw,size=8k,mode=755,uid=1000000,gid=1000000")
(ent "/etc" ignore "ro,nosuid,nodev,relatime" "ext4" "/dev/disk/by-label/nixos" "rw")
@@ -190,7 +191,6 @@
(ent "/var/lib/hakurei/u0/a0" "/var/lib/hakurei/u0/a0" "rw,nosuid,nodev,relatime" "ext4" "/dev/disk/by-label/nixos" "rw")
(ent ignore "/etc/passwd" "ro,nosuid,nodev,relatime" "tmpfs" "rootfs" "rw,uid=1000000,gid=1000000")
(ent ignore "/etc/group" "ro,nosuid,nodev,relatime" "tmpfs" "rootfs" "rw,uid=1000000,gid=1000000")
- (ent "/" "/run/nscd" "rw,nosuid,nodev,relatime" "tmpfs" "ephemeral" "rw,size=8k,mode=755,uid=1000000,gid=1000000")
];
seccomp = true;