From dceb05bf5b65b5539bfd55622c02397d6f2c9acf Mon Sep 17 00:00:00 2001 From: liqiang-fit2cloud Date: Mon, 29 Dec 2025 11:56:49 +0800 Subject: [PATCH] refactor: add env MAXKB_SANDBOX_PYTHON_ALLOW_SYSCALL. --- apps/common/utils/tool_code.py | 4 +++- installer/sandbox.c | 23 ++++++++++++++++------- 2 files changed, 19 insertions(+), 8 deletions(-) diff --git a/apps/common/utils/tool_code.py b/apps/common/utils/tool_code.py index 0185cff10..3731780f6 100644 --- a/apps/common/utils/tool_code.py +++ b/apps/common/utils/tool_code.py @@ -68,9 +68,10 @@ class ToolExecutor: sandbox_conf_file_path = f'{sandbox_lib_path}/.sandbox.conf' if os.path.exists(sandbox_conf_file_path): os.remove(sandbox_conf_file_path) - allow_subprocess = CONFIG.get("SANDBOX_PYTHON_ALLOW_SUBPROCESS", '0') banned_hosts = CONFIG.get("SANDBOX_PYTHON_BANNED_HOSTS", '').strip() allow_dl_paths = CONFIG.get("SANDBOX_PYTHON_ALLOW_DL_PATHS",'').strip() + allow_subprocess = CONFIG.get("SANDBOX_PYTHON_ALLOW_SUBPROCESS", '0') + allow_syscall = CONFIG.get("SANDBOX_PYTHON_ALLOW_SYSCALL", '0') if banned_hosts: hostname = socket.gethostname() local_ip = socket.gethostbyname(hostname) @@ -79,6 +80,7 @@ class ToolExecutor: f.write(f"SANDBOX_PYTHON_BANNED_HOSTS={banned_hosts}\n") f.write(f"SANDBOX_PYTHON_ALLOW_DL_PATHS={','.join(sorted(set(filter(None, sys.path + _sandbox_python_sys_path + allow_dl_paths.split(',')))))}\n") f.write(f"SANDBOX_PYTHON_ALLOW_SUBPROCESS={allow_subprocess}\n") + f.write(f"SANDBOX_PYTHON_ALLOW_SYSCALL={allow_syscall}\n") os.system(f"chmod -R 550 {_sandbox_path}") try: diff --git a/installer/sandbox.c b/installer/sandbox.c index 71cc7f97d..249748b6c 100644 --- a/installer/sandbox.c +++ b/installer/sandbox.c @@ -27,12 +27,14 @@ #define CONFIG_FILE ".sandbox.conf" #define KEY_BANNED_HOSTS "SANDBOX_PYTHON_BANNED_HOSTS" -#define KEY_ALLOW_SUBPROCESS "SANDBOX_PYTHON_ALLOW_SUBPROCESS" #define KEY_ALLOW_DL_PATHS "SANDBOX_PYTHON_ALLOW_DL_PATHS" +#define KEY_ALLOW_SUBPROCESS "SANDBOX_PYTHON_ALLOW_SUBPROCESS" +#define KEY_ALLOW_SYSCALL "SANDBOX_PYTHON_ALLOW_SYSCALL" static char *banned_hosts = NULL; -static int allow_subprocess = 0; // 默认禁止 static char *allow_dl_paths = NULL; +static int allow_subprocess = 0; // 默认禁止 +static int allow_syscall = 0; static void load_sandbox_config() { Dl_info info; @@ -40,6 +42,7 @@ static void load_sandbox_config() { banned_hosts = strdup(""); allow_dl_paths = strdup(""); allow_subprocess = 0; + allow_syscall = 0; return; } char so_path[PATH_MAX]; @@ -53,6 +56,7 @@ static void load_sandbox_config() { banned_hosts = strdup(""); allow_dl_paths = strdup(""); allow_subprocess = 0; + allow_syscall = 0; return; } char line[512]; @@ -61,6 +65,7 @@ static void load_sandbox_config() { banned_hosts = strdup(""); allow_dl_paths = strdup(""); allow_subprocess = 0; + allow_syscall = 0; while (fgets(line, sizeof(line), fp)) { char *key = strtok(line, "="); char *value = strtok(NULL, "\n"); @@ -79,6 +84,8 @@ static void load_sandbox_config() { allow_dl_paths = strdup(value); // 逗号分隔字符串 } else if (strcmp(key, KEY_ALLOW_SUBPROCESS) == 0) { allow_subprocess = atoi(value); + } else if (strcmp(key, KEY_ALLOW_SYSCALL) == 0) { + allow_syscall = atoi(value); } } fclose(fp); @@ -427,6 +434,10 @@ pid_t __forkpty(int *amaster, char *name, const struct termios *termp, const str return forkpty(amaster, name, termp, winp); } /* syscall wrapper to intercept syscalls that directly create processes */ +static int allow_access_syscall() { + ensure_config_loaded(); + return allow_syscall || !is_sandbox_user(); +} long (*real_syscall)(long, ...) = NULL; long syscall(long number, ...) { RESOLVE_REAL(syscall); @@ -456,9 +467,6 @@ long syscall(long number, ...) { #ifdef SYS_posix_spawnp case SYS_posix_spawnp: #endif - if (!allow_create_subprocess()) return deny(); - } - switch (number) { case SYS_socket: case SYS_connect: case SYS_bind: @@ -496,11 +504,12 @@ long syscall(long number, ...) { case SYS_shmget: case SYS_shmctl: case SYS_prctl: - if (is_sandbox_user()) { + if (!allow_access_syscall()) { fprintf(stderr, "Permission denied to access syscall %ld.\n", number); + errno = EACCES; _exit(126); return -1; - } + } } return real_syscall(number, a1, a2, a3, a4, a5, a6); }