2021-04-09 20:39:41 +03:00
#!/bin/bash
2021-10-17 19:13:06 +03:00
# SPDX-License-Identifier: LGPL-2.1-or-later
2018-04-13 16:32:25 +03:00
#
# Basic tests for types creating/writing files
2021-04-09 20:39:41 +03:00
set -eux
set -o pipefail
2018-04-13 16:32:25 +03:00
rm -fr /tmp/{ f,F,w}
mkdir /tmp/{ f,F,w}
touch /tmp/file-owned-by-root
#
# 'f'
#
systemd-tmpfiles --create - <<EOF
f /tmp/f/1 0644 - - - -
f /tmp/f/2 0644 - - - This string should be written
EOF
### '1' should exist and be empty
2021-04-08 00:24:25 +03:00
test -f /tmp/f/1; test ! -s /tmp/f/1
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/f/1) " = "root:root:644"
2018-04-13 16:32:25 +03:00
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/f/2) " = "root:root:644"
2018-04-13 16:32:25 +03:00
test " $( < /tmp/f/2) " = "This string should be written"
### The perms are supposed to be updated even if the file already exists.
systemd-tmpfiles --create - <<EOF
2018-08-06 21:56:45 +03:00
f /tmp/f/1 0666 daemon daemon - This string should not be written
2018-04-13 16:32:25 +03:00
EOF
# file should be empty
2021-04-08 00:24:25 +03:00
test ! -s /tmp/f/1
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/f/1) " = "daemon:daemon:666"
2018-04-13 16:32:25 +03:00
### But we shouldn't try to set perms on an existing file which is not a
### regular one.
mkfifo /tmp/f/fifo
chmod 644 /tmp/f/fifo
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-08-06 21:56:45 +03:00
f /tmp/f/fifo 0666 daemon daemon - This string should not be written
2018-04-13 16:32:25 +03:00
EOF
test -p /tmp/f/fifo
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/f/fifo) " = "root:root:644"
2018-04-13 16:32:25 +03:00
### 'f' should not follow symlinks.
ln -s missing /tmp/f/dangling
ln -s /tmp/file-owned-by-root /tmp/f/symlink
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-08-06 21:56:45 +03:00
f /tmp/f/dangling 0644 daemon daemon - -
f /tmp/f/symlink 0644 daemon daemon - -
2018-04-13 16:32:25 +03:00
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/f/missing
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/file-owned-by-root) " = "root:root:644"
2018-04-13 16:32:25 +03:00
### Handle read-only filesystem gracefully: we shouldn't fail if the target
### already exists and have the correct perms.
mkdir /tmp/f/rw-fs
mkdir /tmp/f/ro-fs
touch /tmp/f/rw-fs/foo
chmod 644 /tmp/f/rw-fs/foo
mount -o bind,ro /tmp/f/rw-fs /tmp/f/ro-fs
systemd-tmpfiles --create - <<EOF
f /tmp/f/ro-fs/foo 0644 - - - - This string should not be written
EOF
2021-04-08 00:24:25 +03:00
test -f /tmp/f/ro-fs/foo; test ! -s /tmp/f/ro-fs/foo
2018-04-13 16:32:25 +03:00
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
f /tmp/f/ro-fs/foo 0666 - - - -
EOF
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/f/fifo) " = "root:root:644"
2018-04-13 16:32:25 +03:00
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
f /tmp/f/ro-fs/bar 0644 - - - -
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/f/ro-fs/bar
2018-04-13 16:32:25 +03:00
### 'f' shouldn't follow unsafe paths.
2018-08-06 21:56:45 +03:00
mkdir /tmp/f/daemon
ln -s /root /tmp/f/daemon/unsafe-symlink
chown -R --no-dereference daemon:daemon /tmp/f/daemon
2018-04-13 16:32:25 +03:00
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-08-06 21:56:45 +03:00
f /tmp/f/daemon/unsafe-symlink/exploit 0644 daemon daemon - -
2018-04-13 16:32:25 +03:00
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/f/daemon/unsafe-symlink/exploit
2018-04-13 16:32:25 +03:00
#
# 'F'
#
echo "This should be truncated" >/tmp/F/truncated
echo "This should be truncated" >/tmp/F/truncated-with-content
systemd-tmpfiles --create - <<EOF
F /tmp/F/created 0644 - - - -
F /tmp/F/created-with-content 0644 - - - new content
2018-08-06 21:56:45 +03:00
F /tmp/F/truncated 0666 daemon daemon - -
F /tmp/F/truncated-with-content 0666 daemon daemon - new content
2018-04-13 16:32:25 +03:00
EOF
2021-04-08 00:24:25 +03:00
test -f /tmp/F/created; test ! -s /tmp/F/created
2018-04-13 16:32:25 +03:00
test -f /tmp/F/created-with-content
test " $( < /tmp/F/created-with-content) " = "new content"
2021-04-08 00:24:25 +03:00
test -f /tmp/F/truncated; test ! -s /tmp/F/truncated
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/F/truncated) " = "daemon:daemon:666"
2018-04-13 16:32:25 +03:00
test -s /tmp/F/truncated-with-content
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/F/truncated-with-content) " = "daemon:daemon:666"
2018-04-13 16:32:25 +03:00
### We shouldn't try to truncate anything but regular files since the behavior is
### unspecified in the other cases.
mkfifo /tmp/F/fifo
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
F /tmp/F/fifo 0644 - - - -
EOF
test -p /tmp/F/fifo
### 'F' should not follow symlinks.
ln -s missing /tmp/F/dangling
ln -s /tmp/file-owned-by-root /tmp/F/symlink
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-08-06 21:56:45 +03:00
f /tmp/F/dangling 0644 daemon daemon - -
f /tmp/F/symlink 0644 daemon daemon - -
2018-04-13 16:32:25 +03:00
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/F/missing
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/file-owned-by-root) " = "root:root:644"
2018-04-13 16:32:25 +03:00
### Handle read-only filesystem gracefully: we shouldn't fail if the target
### already exists and is empty.
mkdir /tmp/F/rw-fs
mkdir /tmp/F/ro-fs
touch /tmp/F/rw-fs/foo
chmod 644 /tmp/F/rw-fs/foo
mount -o bind,ro /tmp/F/rw-fs /tmp/F/ro-fs
systemd-tmpfiles --create - <<EOF
F /tmp/F/ro-fs/foo 0644 - - - -
EOF
2021-04-08 00:24:25 +03:00
test -f /tmp/F/ro-fs/foo; test ! -s /tmp/F/ro-fs/foo
2018-04-13 16:32:25 +03:00
echo "truncating is not allowed anymore" >/tmp/F/rw-fs/foo
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
F /tmp/F/ro-fs/foo 0644 - - - -
EOF
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
F /tmp/F/ro-fs/foo 0644 - - - - This string should not be written
EOF
2021-04-08 00:32:14 +03:00
test -f /tmp/F/ro-fs/foo
grep -q 'truncating is not allowed' /tmp/F/ro-fs/foo
2018-04-13 16:32:25 +03:00
# Trying to change the perms should fail.
2021-04-09 20:52:46 +03:00
: >/tmp/F/rw-fs/foo
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
F /tmp/F/ro-fs/foo 0666 - - - -
EOF
2021-04-09 20:49:32 +03:00
test " $( stat -c %U:%G:%a /tmp/F/ro-fs/foo) " = "root:root:644"
2018-04-13 16:32:25 +03:00
### Try to create a new file.
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
F /tmp/F/ro-fs/bar 0644 - - - -
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/F/ro-fs/bar
2018-04-13 16:32:25 +03:00
### 'F' shouldn't follow unsafe paths.
2018-08-06 21:56:45 +03:00
mkdir /tmp/F/daemon
ln -s /root /tmp/F/daemon/unsafe-symlink
chown -R --no-dereference daemon:daemon /tmp/F/daemon
2018-04-13 16:32:25 +03:00
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-08-06 21:56:45 +03:00
F /tmp/F/daemon/unsafe-symlink/exploit 0644 daemon daemon - -
2018-04-13 16:32:25 +03:00
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/F/daemon/unsafe-symlink/exploit
2018-04-13 16:32:25 +03:00
#
# 'w'
#
touch /tmp/w/overwritten
### nop if the target does not exist.
systemd-tmpfiles --create - <<EOF
w /tmp/w/unexistent 0644 - - - new content
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/w/unexistent
2018-04-13 16:32:25 +03:00
### no argument given -> fails.
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-04-13 16:32:25 +03:00
w /tmp/w/unexistent 0644 - - - -
EOF
### write into an empty file.
systemd-tmpfiles --create - <<EOF
w /tmp/w/overwritten 0644 - - - old content
EOF
test -f /tmp/w/overwritten
test " $( < /tmp/w/overwritten) " = "old content"
### new content is overwritten
systemd-tmpfiles --create - <<EOF
w /tmp/w/overwritten 0644 - - - new content
EOF
test -f /tmp/w/overwritten
test " $( < /tmp/w/overwritten) " = "new content"
2019-04-27 03:22:40 +03:00
### writing into an 'exotic' file should be allowed.
2018-04-13 16:32:25 +03:00
systemd-tmpfiles --create - <<EOF
w /dev/null - - - - new content
EOF
### 'w' follows symlinks
ln -s ./overwritten /tmp/w/symlink
systemd-tmpfiles --create - <<EOF
w /tmp/w/symlink - - - - $( readlink -e /tmp/w/symlink)
EOF
readlink -e /tmp/w/symlink
test " $( < /tmp/w/overwritten) " = "/tmp/w/overwritten"
### 'w' shouldn't follow unsafe paths.
2018-08-06 21:56:45 +03:00
mkdir /tmp/w/daemon
ln -s /root /tmp/w/daemon/unsafe-symlink
chown -R --no-dereference daemon:daemon /tmp/w/daemon
2018-04-13 16:32:25 +03:00
2021-04-08 02:27:33 +03:00
systemd-tmpfiles --create - <<EOF && { echo 'unexpected success' ; exit 1; }
2018-08-06 21:56:45 +03:00
f /tmp/w/daemon/unsafe-symlink/exploit 0644 daemon daemon - -
2018-04-13 16:32:25 +03:00
EOF
2021-04-08 00:24:25 +03:00
test ! -e /tmp/w/daemon/unsafe-symlink/exploit