Kaynağa Gözat

Kernel: Make sys$getsid not require the big lock

Reorganize the code slightly to avoid creating a TOCTOU bug, then mark
the syscall as not needing the big lock anymore.
Andreas Kling 2 yıl önce
ebeveyn
işleme
41f5598516
2 değiştirilmiş dosya ile 8 ekleme ve 7 silme
  1. 1 1
      Kernel/API/Syscall.h
  2. 7 6
      Kernel/Syscalls/setpgid.cpp

+ 1 - 1
Kernel/API/Syscall.h

@@ -104,7 +104,7 @@ enum class NeedsBigProcessLock {
     S(getresgid, NeedsBigProcessLock::No)                   \
     S(getresuid, NeedsBigProcessLock::No)                   \
     S(getrusage, NeedsBigProcessLock::Yes)                  \
-    S(getsid, NeedsBigProcessLock::Yes)                     \
+    S(getsid, NeedsBigProcessLock::No)                      \
     S(getsockname, NeedsBigProcessLock::Yes)                \
     S(getsockopt, NeedsBigProcessLock::No)                  \
     S(gettid, NeedsBigProcessLock::No)                      \

+ 7 - 6
Kernel/Syscalls/setpgid.cpp

@@ -12,16 +12,17 @@ namespace Kernel {
 
 ErrorOr<FlatPtr> Process::sys$getsid(pid_t pid)
 {
-    VERIFY_PROCESS_BIG_LOCK_ACQUIRED(this);
+    VERIFY_NO_PROCESS_BIG_LOCK(this);
     TRY(require_promise(Pledge::stdio));
-    if (pid == 0)
+    if (pid == 0 || pid == this->pid())
         return sid().value();
-    auto process = Process::from_pid_in_same_jail(pid);
-    if (!process)
+    auto peer = Process::from_pid_in_same_jail(pid);
+    if (!peer)
         return ESRCH;
-    if (sid() != process->sid())
+    auto peer_sid = peer->sid();
+    if (sid() != peer_sid)
         return EPERM;
-    return process->sid().value();
+    return peer_sid.value();
 }
 
 ErrorOr<FlatPtr> Process::sys$setsid()