Browse Source

change(proclist): remove tty_idx

greatbridf 1 year ago
parent
commit
ec19ff3095
3 changed files with 77 additions and 103 deletions
  1. 34 40
      include/kernel/process.hpp
  2. 29 51
      src/kernel/process.cpp
  3. 14 12
      src/kernel/syscall.cpp

+ 34 - 40
include/kernel/process.hpp

@@ -352,25 +352,36 @@ public:
     pid_t pgid;
     pid_t sid;
 
+    tty* control_tty;
+
 public:
     // if waitlist is not empty or mutex in cv_wait
     // is locked, its behavior is undefined
-    process(process&& val);
+    constexpr process(process&& val)
+        : mms(std::move(val.mms))
+        , thds { std::move(val.thds), this }
+        , attr { val.attr }
+        , files(std::move(val.files))
+        , pwd(std::move(val.pwd))
+        , pid(val.pid)
+        , ppid(val.ppid)
+        , pgid(val.pgid)
+        , sid(val.sid)
+    {
+        if (current_process == &val)
+            current_process = this;
+    }
+
     process(const process&);
 
-    explicit process(pid_t ppid,
-        bool system = true,
-        types::string<>&& path = "/",
-        kernel::signal_list&& sigs = {});
+    // this function is used for system initialization
+    // DO NOT use this after the system is on
+    explicit process(pid_t ppid);
 
     constexpr bool is_system(void) const
-    {
-        return attr.system;
-    }
+    { return attr.system; }
     constexpr bool is_zombie(void) const
-    {
-        return attr.zombie;
-    }
+    { return attr.zombie; }
 
 private:
     static inline pid_t max_pid;
@@ -385,14 +396,12 @@ class proclist final {
 public:
     using list_type = types::map<pid_t, process>;
     using child_index_type = types::hash_map<pid_t, types::list<pid_t>>;
-    using tty_index_type = types::map<pid_t, tty*>;
     using iterator_type = list_type::iterator_type;
     using const_iterator_type = list_type::const_iterator_type;
 
 private:
     list_type m_procs;
     child_index_type m_child_idx;
-    tty_index_type m_tty_idx;
 
 public:
     template <typename... Args>
@@ -414,25 +423,6 @@ public:
         return iter;
     }
 
-    constexpr void set_ctrl_tty(pid_t pid, tty* _tty)
-    {
-        auto iter = m_tty_idx.find(pid);
-        _tty->set_pgrp(pid);
-        if (iter) {
-            iter->second = _tty;
-        } else {
-            m_tty_idx.insert(std::make_pair(pid, _tty));
-        }
-    }
-
-    constexpr tty* get_ctrl_tty(pid_t pid)
-    {
-        auto iter = m_tty_idx.find(pid);
-        if (!iter)
-            return nullptr;
-        return iter->second;
-    }
-
     constexpr void remove(pid_t pid)
     {
         make_children_orphans(pid);
@@ -448,12 +438,17 @@ public:
         m_procs.erase(proc_iter);
     }
 
-    constexpr process* find(pid_t pid)
+    constexpr bool try_find(pid_t pid) const
+    {
+        return !!m_procs.find(pid);
+    }
+
+    // if process doesn't exist, the behavior is undefined
+    constexpr process& find(pid_t pid)
     {
         auto iter = m_procs.find(pid);
-        // TODO: change this
         assert(!!iter);
-        return &iter->second;
+        return iter->second;
     }
 
     constexpr bool has_child(pid_t pid)
@@ -472,18 +467,17 @@ public:
 
         for (auto item : children->second) {
             init_children->second.push_back(item);
-            find(item)->ppid = 1;
+            find(item).ppid = 1;
         }
 
         m_child_idx.remove(children);
     }
 
+    // the process MUST exist, or the behavior is undefined
     void send_signal(pid_t pid, kernel::sig_t signal)
     {
-        auto iter = this->find(pid);
-        if (!iter)
-            return;
-        iter->signals.set(signal);
+        auto proc = this->find(pid);
+        proc.signals.set(signal);
     }
     void send_signal_grp(pid_t pgid, kernel::sig_t signal)
     {

+ 29 - 51
src/kernel/process.cpp

@@ -92,30 +92,15 @@ void thread::free_kstack(uint32_t p)
     pkstack_bmp->clear(p);
 }
 
-process::process(process&& val)
-    : mms(std::move(val.mms))
-    , thds { std::move(val.thds), this }
-    , attr { val.attr }
-    , files(std::move(val.files))
-    , pwd(std::move(val.pwd))
-    , pid(val.pid)
-    , ppid(val.ppid)
-    , pgid(val.pgid)
-    , sid(val.sid)
-{
-    if (current_process == &val)
-        current_process = this;
-}
-
 process::process(const process& parent)
-    : process { parent.pid,
-        parent.is_system(),
-        types::string<>(parent.pwd),
-        kernel::signal_list(parent.signals) }
+    : mms { *kernel_mms }
+    , attr { .system = parent.is_system() }
+    , pwd { parent.pwd }
+    , signals { parent.signals }
+    , pid { process::alloc_pid() }
+    , ppid { parent.pid } , pgid { parent.pgid } , sid { parent.sid }
+    , control_tty { parent.control_tty }
 {
-    this->pgid = parent.pgid;
-    this->sid = parent.sid;
-
     for (auto& area : parent.mms) {
         if (area.is_kernel_space() || area.attr.in.system)
             continue;
@@ -126,39 +111,32 @@ process::process(const process& parent)
     this->files.dup_all(parent.files);
 }
 
-process::process(pid_t _ppid,
-    bool _system,
-    types::string<>&& path,
-    kernel::signal_list&& _sigs)
+process::process(pid_t ppid)
     : mms(*kernel_mms)
-    , attr { .system = _system }
-    , pwd { std::move(path) }
-    , signals(std::move(_sigs))
+    , attr { .system = true }
+    , pwd { "/" }
     , pid { process::alloc_pid() }
-    , ppid { _ppid }
-    , pgid { 0 }
-    , sid { 0 }
-{
-}
+    , ppid { ppid }
+    , pgid {} , sid {} , control_tty {} { }
 
 void proclist::kill(pid_t pid, int exit_code)
 {
-    process* proc = this->find(pid);
+    auto& proc = this->find(pid);
 
     // remove threads from ready list
-    for (auto& thd : proc->thds.underlying_list()) {
+    for (auto& thd : proc.thds.underlying_list()) {
         thd.attr.ready = 0;
         readythds->remove_all(&thd);
     }
 
     // write back mmap'ped files and close them
-    proc->files.close_all();
+    proc.files.close_all();
 
     // unmap all user memory areas
-    proc->mms.clear_user();
+    proc.mms.clear_user();
 
     // init should never exit
-    if (proc->ppid == 0) {
+    if (proc.ppid == 0) {
         console->print("kernel panic: init exited!\n");
         assert(false);
     }
@@ -166,38 +144,38 @@ void proclist::kill(pid_t pid, int exit_code)
     // make child processes orphans (children of init)
     this->make_children_orphans(pid);
 
-    proc->attr.zombie = 1;
+    proc.attr.zombie = 1;
 
     // notify parent process and init
-    auto* parent = this->find(proc->ppid);
-    auto* init = this->find(1);
+    auto& parent = this->find(proc.ppid);
+    auto& init = this->find(1);
 
     bool flag = false;
     {
-        auto& mtx = init->cv_wait.mtx();
+        auto& mtx = init.cv_wait.mtx();
         types::lock_guard lck(mtx);
 
         {
-            auto& mtx = proc->cv_wait.mtx();
+            auto& mtx = proc.cv_wait.mtx();
             types::lock_guard lck(mtx);
 
-            for (const auto& item : proc->waitlist) {
-                init->waitlist.push_back(item);
+            for (const auto& item : proc.waitlist) {
+                init.waitlist.push_back(item);
                 flag = true;
             }
 
-            proc->waitlist.clear();
+            proc.waitlist.clear();
         }
     }
     if (flag)
-        init->cv_wait.notify();
+        init.cv_wait.notify();
 
     {
-        auto& mtx = parent->cv_wait.mtx();
+        auto& mtx = parent.cv_wait.mtx();
         types::lock_guard lck(mtx);
-        parent->waitlist.push_back({ pid, exit_code });
+        parent.waitlist.push_back({ pid, exit_code });
     }
-    parent->cv_wait.notify();
+    parent.cv_wait.notify();
 }
 
 void kernel_threadd_main(void)

+ 14 - 12
src/kernel/syscall.cpp

@@ -301,7 +301,8 @@ int _syscall_setsid(interrupt_stack*)
     current_process->pgid = current_process->pid;
 
     // TODO: get tty* from fd or block device id
-    procs->set_ctrl_tty(current_process->pid, console);
+    console->set_pgrp(current_process->pid);
+    current_process->control_tty = console;
 
     return current_process->pid;
 }
@@ -310,13 +311,13 @@ int _syscall_getsid(interrupt_stack* data)
 {
     pid_t pid = data->s_regs.edi;
 
-    auto* proc = procs->find(pid);
-    if (!proc)
+    if (!procs->try_find(pid))
         return -ESRCH;
-    if (proc->sid != current_process->sid)
+    auto& proc = procs->find(pid);
+    if (proc.sid != current_process->sid)
         return -EPERM;
 
-    return proc->sid;
+    return proc.sid;
 }
 
 int _syscall_close(interrupt_stack* data)
@@ -359,14 +360,15 @@ int _syscall_setpgid(interrupt_stack* data)
     if (pgid == 0)
         pgid = pid;
 
-    auto* proc = procs->find(pid);
-    // TODO: check whether the process exists
-    // if (!proc)
-    //     return -ESRCH;
+    if (!procs->try_find(pid))
+        return -ESRCH;
+
+    auto& proc = procs->find(pid);
 
     // TODO: check whether pgid and the original
     //       pgid is in the same session
-    proc->pgid = pgid;
+
+    proc.pgid = pgid;
 
     return 0;
 }
@@ -389,7 +391,7 @@ int _syscall_ioctl(interrupt_stack* data)
     switch (request) {
     case TIOCGPGRP: {
         auto* pgid = (pid_t*)data->s_regs.edx;
-        tty* ctrl_tty = procs->get_ctrl_tty(current_process->pid);
+        tty* ctrl_tty = current_process->control_tty;
         // TODO: copy_to_user
         *pgid = ctrl_tty->get_pgrp();
         break;
@@ -397,7 +399,7 @@ int _syscall_ioctl(interrupt_stack* data)
     case TIOCSPGRP: {
         // TODO: copy_from_user
         pid_t pgid = *(const pid_t*)data->s_regs.edx;
-        tty* ctrl_tty = procs->get_ctrl_tty(current_process->pid);
+        tty* ctrl_tty = current_process->control_tty;
         ctrl_tty->set_pgrp(pgid);
         break;
     }