summaryrefslogtreecommitdiff
path: root/kernel/pgrp.cc
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/pgrp.cc')
-rw-r--r--kernel/pgrp.cc148
1 files changed, 0 insertions, 148 deletions
diff --git a/kernel/pgrp.cc b/kernel/pgrp.cc
deleted file mode 100644
index e5b382c..0000000
--- a/kernel/pgrp.cc
+++ /dev/null
@@ -1,148 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0-or-later */
-/* Copyright (C) 2026 Richard Qin */
-
-/*
- * Process Group / Session Implementation
- *
- * Hash table of signal_struct objects keyed by pgid. Lifecycle of
- * signal_struct mirrors Linux: one per thread group, refcounted across
- * CLONE_THREAD siblings, freed when the last task in the group exits.
- *
- * Reference: Linux kernel/pid.c, kernel/exit.c
- */
-
-#include <lume/pgrp.h>
-#include <lume/signal_types.h>
-#include <lume/task.h>
-#include <lume/new.h>
-#include <lume/klog.h>
-
-/* ================================================================== */
-/* Hash table state */
-/* ================================================================== */
-
-list_node g_pgrp_hash[kPgrpHashSize];
-Spinlock g_pgrp_lock;
-
-void pgrp_init()
-{
- for (auto& bucket : g_pgrp_hash) bucket.init();
- g_pgrp_lock.init("pgrp");
-}
-
-/* ================================================================== */
-/* Internal helpers (must be called with g_pgrp_lock held) */
-/* ================================================================== */
-
-static void pgrp_attach_locked(signal_struct* sig, int32 pgid)
-{
- sig->pgid = pgid;
- list_node* bucket = &g_pgrp_hash[pgrp_hash_idx(pgid)];
- sig->pgrp_link.prev = bucket->prev;
- sig->pgrp_link.next = bucket;
- bucket->prev->next = &sig->pgrp_link;
- bucket->prev = &sig->pgrp_link;
-}
-
-static void pgrp_detach_locked(signal_struct* sig)
-{
- /* Unlink only if currently on a list — init() makes prev/next point
- * to self, which we treat as "not linked". */
- if (sig->pgrp_link.next == &sig->pgrp_link) return;
- sig->pgrp_link.prev->next = sig->pgrp_link.next;
- sig->pgrp_link.next->prev = sig->pgrp_link.prev;
- sig->pgrp_link.init();
-}
-
-/* ================================================================== */
-/* signal_struct allocation / refcount */
-/* ================================================================== */
-
-signal_struct* alloc_signal_struct(int32 leader_pid, TaskControlBlock* leader)
-{
- auto* sig = new signal_struct;
- if (!sig) return nullptr;
- sig->init(leader_pid, leader);
-
- LockGuard guard(g_pgrp_lock);
- pgrp_attach_locked(sig, leader_pid);
- return sig;
-}
-
-signal_struct* fork_signal_struct(signal_struct* parent,
- TaskControlBlock* child_leader)
-{
- if (!parent) return nullptr;
-
- auto* sig = new signal_struct;
- if (!sig) return nullptr;
-
- /* Copy identity from parent, then override leader and attach. */
- sig->lock.init("signal");
- sig->refcount = 1;
- sig->leader = child_leader;
- sig->tty_old_pgrp = 0;
- sig->pgrp_link.init();
-
- {
- LockGuard pg(parent->lock);
- sig->pgid = parent->pgid;
- sig->sid = parent->sid;
- sig->tty = parent->tty;
- }
-
- LockGuard guard(g_pgrp_lock);
- pgrp_attach_locked(sig, sig->pgid);
- return sig;
-}
-
-void get_signal_struct(signal_struct* sig)
-{
- if (!sig) return;
- LockGuard guard(sig->lock);
- sig->refcount++;
-}
-
-void put_signal_struct(signal_struct* sig)
-{
- if (!sig) return;
-
- uint32 remaining;
- {
- LockGuard guard(sig->lock);
- remaining = --sig->refcount;
- }
- if (remaining != 0) return;
-
- /* Last reference — detach from pgrp hash and free. */
- {
- LockGuard guard(g_pgrp_lock);
- pgrp_detach_locked(sig);
- }
- delete sig;
-}
-
-/* ================================================================== */
-/* Pgrp membership change */
-/* ================================================================== */
-
-void change_pgid(signal_struct* sig, int32 new_pgid)
-{
- if (!sig) return;
- LockGuard guard(g_pgrp_lock);
- if (sig->pgid == new_pgid) return;
- pgrp_detach_locked(sig);
- pgrp_attach_locked(sig, new_pgid);
-}
-
-int pgrp_member_count(int32 pgid)
-{
- LockGuard guard(g_pgrp_lock);
- int n = 0;
- list_node* bucket = &g_pgrp_hash[pgrp_hash_idx(pgid)];
- for (list_node* node = bucket->next; node != bucket; node = node->next) {
- auto* sig = list_entry<signal_struct, &signal_struct::pgrp_link>(node);
- if (sig->pgid == pgid) n++;
- }
- return n;
-}