Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

tests: spread test from #12849 in isolation #12856

Closed
wants to merge 4 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 29 additions & 0 deletions tests/main/snap-seccomp-blocks-tty-injection/task.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
summary: Ensure that the snap-seccomp blocks tty command injection

# ubuntu-core: excluded because there is no gcc there
systems: [-ubuntu-core-*]

prepare: |
echo "Install a helper snap (for seccomp confinement testing)"
"$TESTSTOOLS"/snaps-state install-local test-snapd-sh

echo "Compile and prepare the test programs"
# Because we use the snap data directory we don't need to clean it up
# manually as all snaps and their data are reset after each test.
# Build the test binary statically, as it will be running inside a base with
# potentially older glibc.
gcc -Wall -Wextra -Werror ./test-tioclinux.c -o /var/snap/test-snapd-sh/common/test-tioclinux -static
gcc -Wall -Wextra -Werror ./test-tiocsti.c -o /var/snap/test-snapd-sh/common/test-tiocsti -static

execute: |
# use /dev/tty1 as input so that we use a real virtual console which
# supports TIOCSTI / TIOCLINUX - but first make sure the snap can access it
# through AppArmor
if [ "$(snap debug confinement)" = strict ]; then
sed -i 's|^}$| /dev/tty1 rw,\n}|' /var/lib/snapd/apparmor/profiles/snap.test-snapd-sh.sh
apparmor_parser -r /var/lib/snapd/apparmor/profiles/snap.test-snapd-sh.sh
fi

snap run test-snapd-sh.sh -c "\$SNAP_COMMON/test-tiocsti" < /dev/tty1 2>&1 | MATCH 'normal TIOCSTI: -1 \(Operation not permitted\)'
snap run test-snapd-sh.sh -c "\$SNAP_COMMON/test-tiocsti" < /dev/tty1 2>&1 | MATCH 'high-bit-set TIOCSTI: -1 \(Operation not permitted\)'
snap run test-snapd-sh.sh -c "\$SNAP_COMMON/test-tioclinux" < /dev/tty1 2>&1 | MATCH 'ioctl\(0, TIOCLINUX, ...\) failed: Operation not permitted'
36 changes: 36 additions & 0 deletions tests/main/snap-seccomp-blocks-tty-injection/test-tioclinux.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
#include <err.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/ioctl.h>

#include <linux/tiocl.h>
#include <linux/vt.h>

int main(void)
{
int res;
printf("\33[H\33[2J");
printf("head -n1 /etc/shadow\n");
fflush(stdout);
struct {
char padding;
char subcode;
struct tiocl_selection sel;
} data = {
.subcode = TIOCL_SETSEL,
.sel = {
.xs = 1, .ys = 1,
.xe = 1, .ye = 1,
.sel_mode = TIOCL_SELLINE
}
};
res = ioctl(0, TIOCLINUX, &data.subcode);
if (res != 0)
err(EXIT_FAILURE, "ioctl(0, TIOCLINUX, ...) failed");
data.subcode = TIOCL_PASTESEL;
ioctl(0, TIOCLINUX, &data.subcode);
if (res != 0)
err(EXIT_FAILURE, "ioctl(0, TIOCLINUX, ...) failed");
exit(EXIT_SUCCESS);
}

30 changes: 30 additions & 0 deletions tests/main/snap-seccomp-blocks-tty-injection/test-tiocsti.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
#define _GNU_SOURCE
#include <termios.h>
#include <sys/ioctl.h>
#include <unistd.h>
#include <stdio.h>
#include <sys/syscall.h>
#include <errno.h>

static int ioctl64(int fd, unsigned long nr, void *arg) {
errno = 0;
return syscall(__NR_ioctl, fd, nr, arg);
}

int main(void) {
int res;
char pushmeback = '#';

unsigned long syscallnr = TIOCSTI;
res = ioctl64(0, syscallnr, &pushmeback);
printf("normal TIOCSTI: %d (%m)\n", res);

#ifdef __LP64__
// this high bit check only works on 64bit systems, on 32bit it will fail:
// "error: left shift count >= width of type [-Werror=shift-count-overflow]"
syscallnr = TIOCSTI | (1UL<<32);
#endif
res = ioctl64(0, syscallnr, &pushmeback);
printf("high-bit-set TIOCSTI: %d (%m)\n", res);
return res;
}