diff options
author | Andreas Kling <kling@serenityos.org> | 2021-03-10 19:59:46 +0100 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2021-03-10 22:30:02 +0100 |
commit | cbcf891040e9921ff628fdda668c9738f358a178 (patch) | |
tree | 6f50101dc6c2993361fa4436923927faa98c6e14 /Kernel/Syscalls/execve.cpp | |
parent | 839d2d70a4bd73d9162a03430c20c1ee2e542331 (diff) | |
download | serenity-cbcf891040e9921ff628fdda668c9738f358a178.zip |
Kernel: Move select Process members into protected memory
Process member variable like m_euid are very valuable targets for
kernel exploits and until now they have been writable at all times.
This patch moves m_euid along with a whole bunch of other members
into a new Process::ProtectedData struct. This struct is remapped
as read-only memory whenever we don't need to write to it.
This means that a kernel write primitive is no longer enough to
overwrite a process's effective UID, you must first unprotect the
protected data where the UID is stored. :^)
Diffstat (limited to 'Kernel/Syscalls/execve.cpp')
-rw-r--r-- | Kernel/Syscalls/execve.cpp | 14 |
1 files changed, 9 insertions, 5 deletions
diff --git a/Kernel/Syscalls/execve.cpp b/Kernel/Syscalls/execve.cpp index 03de8d0df6..5aa2e8686e 100644 --- a/Kernel/Syscalls/execve.cpp +++ b/Kernel/Syscalls/execve.cpp @@ -507,11 +507,15 @@ KResult Process::do_exec(NonnullRefPtr<FileDescription> main_program_description if (!(main_program_description->custody()->mount_flags() & MS_NOSUID)) { if (main_program_metadata.is_setuid()) { executable_is_setid = true; - m_euid = m_suid = main_program_metadata.uid; + MutableProtectedData protected_data { *this }; + protected_data->euid = main_program_metadata.uid; + protected_data->suid = main_program_metadata.uid; } if (main_program_metadata.is_setgid()) { executable_is_setid = true; - m_egid = m_sgid = main_program_metadata.gid; + MutableProtectedData protected_data { *this }; + protected_data->egid = main_program_metadata.gid; + protected_data->sgid = main_program_metadata.gid; } } @@ -574,7 +578,7 @@ KResult Process::do_exec(NonnullRefPtr<FileDescription> main_program_description } VERIFY(new_main_thread); - auto auxv = generate_auxiliary_vector(load_result.load_base, load_result.entry_eip, m_uid, m_euid, m_gid, m_egid, path, main_program_fd); + auto auxv = generate_auxiliary_vector(load_result.load_base, load_result.entry_eip, uid(), euid(), gid(), egid(), path, main_program_fd); // NOTE: We create the new stack before disabling interrupts since it will zero-fault // and we don't want to deal with faults after this point. @@ -600,7 +604,7 @@ KResult Process::do_exec(NonnullRefPtr<FileDescription> main_program_description new_main_thread->set_name(m_name); // FIXME: PID/TID ISSUE - m_pid = new_main_thread->tid().value(); + MutableProtectedData(*this)->pid = new_main_thread->tid().value(); auto tsr_result = new_main_thread->make_thread_specific_region({}); if (tsr_result.is_error()) { // FIXME: We cannot fail this late. Refactor this so the allocation happens before we commit to the new executable. @@ -618,7 +622,7 @@ KResult Process::do_exec(NonnullRefPtr<FileDescription> main_program_description tss.eip = load_result.entry_eip; tss.esp = new_userspace_esp; tss.cr3 = space().page_directory().cr3(); - tss.ss2 = m_pid.value(); + tss.ss2 = pid().value(); // Throw away any recorded performance events in this process. if (m_perf_event_buffer) |