I'm trying to execute C/C++ code in a secure environment using Seccomp and Ececve. But, C/C++ code is not being executed while trying with this setup. Please look at the files.

seccomp_rules.c

#include <stdio.h>
#include <seccomp.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdbool.h>

#include "seccomp_rules.h"


int c_cpp_seccomp_rules(struct config *_config, bool allow_write_file)
{

    int syscalls_whitelist[] = {SCMP_SYS(read), SCMP_SYS(fstat),
                                SCMP_SYS(mmap), SCMP_SYS(mprotect),
                                SCMP_SYS(munmap), SCMP_SYS(uname),
                                SCMP_SYS(arch_prctl), SCMP_SYS(brk),
                                SCMP_SYS(access), SCMP_SYS(exit_group),
                                SCMP_SYS(close), SCMP_SYS(readlink),
                                SCMP_SYS(sysinfo), SCMP_SYS(write),
                                SCMP_SYS(writev), SCMP_SYS(lseek),
                                SCMP_SYS(clock_gettime), SCMP_SYS(pread64)}; // add extra rule for pread64

    int syscalls_whitelist_length = sizeof(syscalls_whitelist) / sizeof(int);
    scmp_filter_ctx ctx = NULL;

    ctx = seccomp_init(SCMP_ACT_KILL);

    if (!ctx)
    {
        return LOAD_SECCOMP_FAILED;
    }
    for (int i = 0; i < syscalls_whitelist_length; i++)
    {
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, syscalls_whitelist[i], 0) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
    }
    if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(execve), 1, SCMP_A0(SCMP_CMP_EQ, (scmp_datum_t)(_config->exe_path))) != 0)
    {
        return LOAD_SECCOMP_FAILED;
    }
    if (!allow_write_file)
    {
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(open), 1, SCMP_CMP(1, SCMP_CMP_MASKED_EQ, O_WRONLY | O_RDWR, 0)) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(openat), 1, SCMP_CMP(2, SCMP_CMP_MASKED_EQ, O_WRONLY | O_RDWR, 0)) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
    }
    else
    {
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(open), 0) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(dup), 0) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(dup2), 0) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
        if (seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(dup3), 0) != 0)
        {
            return LOAD_SECCOMP_FAILED;
        }
    }

    if (seccomp_load(ctx) != 0)
    {
        return LOAD_SECCOMP_FAILED;
    }
    seccomp_release(ctx);
    return 0;
}

main.c

temp.c is a simple C file, temp is the C object file that I'm trying to execute in the project

#include <stdio.h>
#include <seccomp.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdbool.h>

#include "seccomp_rules.h"

int main()
{

    struct config _config;
    long orig_eax;
    _config.exe_path = "/home/ubuntu/runner/temp";
    _config.args[0] = _config.exe_path;
    _config.args[1] = NULL;
    _config.env[0] = "PATH=/usr/local/bin:/usr/bin:/bin";
    _config.env[1] = "LANG=en_US.UTF-8";
    _config.env[2] = "LANGUAGE=en_US:en";
    _config.env[3] = "LC_ALL=en_US.UTF-8";
    _config.env[4] = NULL;

    pid_t child_pid = fork();

    // pid < 0 shows clone failed
    if (child_pid < 0)
    {
        printf("FORK_FAILED");
    }
    else if (child_pid == 0)
    {
        c_cpp_seccomp_rules(&_config, true);
        execve(_config.exe_path, _config.args, _config.env);
        printf("execve failed\n");
    }
    else if (child_pid > 0)
    {
        
    }
}

seccomp_rules.h

#ifndef SECCOMP_RULES_H
#define SECCOMP_RULES_H
#include <stdbool.h>
#include <sys/types.h>

#define LOAD_SECCOMP_FAILED -1;

struct config
{
    char *exe_path;
    char *args[20];
    char *env[20];
};

int c_cpp_seccomp_rules(struct config *_config, bool allow_write_file);

#endif // SECCOMP_RULES_H

CMakeLists.txt

cmake_minimum_required(VERSION 2.5)
# set(CMAKE_TRY_COMPILE_TARGET_TYPE "STATIC_LIBRARY")
# SET (CMAKE_C_COMPILER_WORKS 1)
# SET (CMAKE_CXX_COMPILER_WORKS 1)
project(Seccomp)

#set(CMAKE_VERBOSE_MAKEFILE ON)
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/output)

set(CMAKE_C_FLAGS "-g -Wall -O3 -std=c99 -pie -fPIC")

file(GLOB SOURCE "./*.c")
add_executable(seccomp.so ${SOURCE})
target_link_libraries(seccomp.so pthread seccomp)


install(FILES output/seccomp.so
    PERMISSIONS OWNER_EXECUTE OWNER_READ
    DESTINATION /usr/lib/runner)

Put all these files in a folder and execute these commands.

  • cmake . && make

  • ./output/seccomp.so

0

There are 0 answers