diff --git a/Kernel/Process.cpp b/Kernel/Process.cpp index 69c407289e..a9e7a28138 100644 --- a/Kernel/Process.cpp +++ b/Kernel/Process.cpp @@ -282,7 +282,7 @@ pid_t Process::sys$fork(RegisterDump& regs) return child->pid(); } -int Process::do_exec(const String& path, Vector&& arguments, Vector&& environment) +int Process::do_exec(String path, Vector arguments, Vector environment) { ASSERT(is_ring3()); @@ -419,11 +419,11 @@ int Process::do_exec(const String& path, Vector&& arguments, Vector&& arguments, Vector&& environment) +int Process::exec(String path, Vector arguments, Vector environment) { // The bulk of exec() is done by do_exec(), which ensures that all locals // are cleaned up by the time we yield-teleport below. - int rc = do_exec(path, move(arguments), move(environment)); + int rc = do_exec(move(path), move(arguments), move(environment)); if (rc < 0) return rc; @@ -436,6 +436,8 @@ int Process::exec(const String& path, Vector&& arguments, Vector int Process::sys$execve(const char* filename, const char** argv, const char** envp) { + // NOTE: Be extremely careful with allocating any kernel memory in exec(). + // On success, the kernel stack will be lost. if (!validate_read_str(filename)) return -EFAULT; if (argv) { @@ -456,24 +458,25 @@ int Process::sys$execve(const char* filename, const char** argv, const char** en } String path(filename); - auto parts = path.split('/'); - Vector arguments; - if (argv) { - for (size_t i = 0; argv[i]; ++i) { - arguments.append(argv[i]); - } - } else { - arguments.append(parts.last()); - } - Vector environment; - if (envp) { - for (size_t i = 0; envp[i]; ++i) - environment.append(envp[i]); + { + auto parts = path.split('/'); + if (argv) { + for (size_t i = 0; argv[i]; ++i) { + arguments.append(argv[i]); + } + } else { + arguments.append(parts.last()); + } + + if (envp) { + for (size_t i = 0; envp[i]; ++i) + environment.append(envp[i]); + } } - int rc = exec(path, move(arguments), move(environment)); + int rc = exec(move(path), move(arguments), move(environment)); ASSERT(rc < 0); // We should never continue after a successful exec! return rc; } diff --git a/Kernel/Process.h b/Kernel/Process.h index bbad42d35e..b44fda0dce 100644 --- a/Kernel/Process.h +++ b/Kernel/Process.h @@ -279,7 +279,7 @@ public: size_t amount_shared() const; Process* fork(RegisterDump&); - int exec(const String& path, Vector&& arguments, Vector&& environment); + int exec(String path, Vector arguments, Vector environment); bool is_root() const { return m_euid == 0; } @@ -302,7 +302,7 @@ private: Process(String&& name, uid_t, gid_t, pid_t ppid, RingLevel, RetainPtr&& cwd = nullptr, RetainPtr&& executable = nullptr, TTY* = nullptr, Process* fork_parent = nullptr); - int do_exec(const String& path, Vector&& arguments, Vector&& environment); + int do_exec(String path, Vector arguments, Vector environment); void push_value_on_stack(dword); int alloc_fd();