/..

#CONTENT

#TOP

seccomp
213 bytes2024-02-29 21:34
chal
16 KiB2024-02-29 21:34
chal.c
2 KiB2024-02-29 21:34
Dockerfile
134 bytes2024-02-29 21:34
flag.txt
40 bytes2024-02-29 21:34
Makefile
415 bytes2024-02-29 21:34
README.mdx
2 KiB2024-08-23 05:19

#Provided Files

chal.c
C
#include <sys/mman.h>
#include <fcntl.h>
#include <unistd.h>
#include <linux/seccomp.h>
#include <seccomp.h>
#include <err.h>
#include <stdio.h>
#include <stdlib.h>

void setup_seccomp () {
    scmp_filter_ctx ctx;
    ctx = seccomp_init(SCMP_ACT_KILL);
    int ret = 0;
    ret |= seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(read), 0);
    ret |= seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(write), 0);
    ret |= seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(exit), 0);
    ret |= seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(exit_group), 0);
    ret |= seccomp_load(ctx);
    if (ret) {
        errx(1, "seccomp failed");
    }
}

int main () {
    setbuf(stdout, NULL);
    setbuf(stderr, NULL);

    alarm(6);

    int fd = open("flag.txt", O_RDONLY);
    if (0 > fd)
        errx(1, "failed to open flag.txt");

    char * flag = mmap(NULL, 0x1000, PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0);
    if (flag == MAP_FAILED)
        errx(1, "failed to mmap memory");

    if (0 > read(fd, flag, 0x1000))
        errx(1, "failed to read flag");

    // make flag write-only
    if (0 > mprotect(flag, 0x1000, PROT_WRITE))
        errx(1, "failed to change mmap permissions");

    char * code = mmap(NULL, 0x100000, PROT_READ | PROT_WRITE | PROT_EXEC, MAP_ANON | MAP_PRIVATE, -1, 0);
    if (code == MAP_FAILED)
        errx(1, "failed to mmap shellcode buffer");

    printf("> ");
    if (0 > read(0, code, 0x100000))
        errx(1, "failed to read shellcode");

    setup_seccomp();

    ((void(*)(char *))code)(flag);
    exit(0);
}

#Intended

In the provided source file, the code does a few things

  1. writes the contents of flag.txt into a mmapped buffer
  2. mprotects the flag memory to PROT_WRITE
  3. mmaps shellcode
  4. setups up seccomp sandbox
  5. executes shellcode

The intended solution is to simply print out the contents of the flag. Even though the memory is set to PROT_WRITE, on x64 there is not concept of write-only memory. On x64 write implies read, so even though the memory protection is set to write-only we can still read the flag.

#Unintendeds

#flag.txt fd is not closed

I forgot to close the flag.txt fd before executing the shellcode, which meants that you could simply read from the flag fd and get the flag.