|
AquilaOS documentation
How it works, and its code
|
Processes: making them and ending them, their IDs, their descriptors, and their sessions and process groups. More...
#include <core/system.h>#include <core/panic.h>#include <core/string.h>#include <core/arch.h>#include <mm/pmap.h>#include <mm/mm.h>#include <mm/vm.h>#include <sys/proc.h>#include <sys/sched.h>#include <fs/vfs.h>#include <dev/tty.h>#include <ds/queue.h>#include <ds/bitmap.h>Go to the source code of this file.
Functions | |
| static int | pid_is_group (int pid) |
| Returns whether a process group or a session has pid as its ID. | |
| int | proc_pid_alloc () |
| Allocates a process ID, from 1 (init's) on. | |
| void | proc_pid_free (int pid) |
| Frees a process ID. | |
| int | proc_new (struct proc **ref) |
| Makes a new process structure, with one thread and an empty address space, on the list of every process. | |
| struct proc * | proc_pid_find (pid_t pid) |
| Finds a process by its ID. | |
| int | proc_init (struct proc *proc) |
| Gives a new process (init) its ID and its descriptor table. | |
| int | pgrp_orphaned (struct pgroup *pgrp, struct proc *gone) |
| Says whether a process group is orphaned (POSIX): none of its members has a parent in another group of the same session, so no one there would continue it once it stops. | |
| static void | pgrp_orphaned_hangup (struct pgroup *pgrp, struct proc *gone) |
| Sends SIGHUP and SIGCONT to a process group that gone leaving makes orphaned, if one of its members is stopped: nothing else would continue them. | |
| static int | pgrp_other_same_session (struct proc *p, struct proc *q) |
| Returns whether p's process group is another group of the same session as q's. | |
| static void | proc_zombie_notify (struct proc *proc) |
| Tells a zombie's parent that it ended: its wait() wakes up and it gets SIGCHLD. | |
| int | proc_threads_end (struct proc *proc, struct thread *keep, int exiting) |
| Ends the threads of a process, but one. | |
| void | proc_threads_exec (struct proc *proc) |
| Ends every thread of a process but the current one, for execve() (POSIX: they run in the program that is replaced). | |
| void | proc_kill (struct proc *proc) |
| Ends a process: its threads end, its descriptors are closed, its memory is freed, its children go to init, and it becomes a zombie that its parent may wait for. | |
| int | proc_reap (struct proc *proc) |
| Frees a zombie, once its parent waited for it (or doesn't wait for its children). | |
| int | proc_fd_get (struct proc *proc) |
| Reserves the lowest free descriptor of a process, while a system call sets it up: no other thread takes it, and it doesn't refer to a file yet. | |
| void | proc_fd_release (struct proc *proc, int fd) |
| Frees a reserved descriptor that wasn't set up after all. | |
| void | proc_fd_install (struct proc *proc, int fd, struct file *file, int flags) |
| Makes a reserved descriptor refer to an open file. | |
| struct file * | proc_fd_file (struct proc *proc, int fd) |
| Finds the open file a descriptor refers to. | |
| int | proc_fd_close (struct proc *proc, int fd) |
| Closes a descriptor: it is free again, and its reference to the open file is dropped. | |
| int | session_new (struct proc *proc) |
| Makes a new session, with a new process group, both led by a process and with its ID, and moves the process into it, as setsid() does. | |
| int | proc_setpgid (struct proc *proc, pid_t pgid) |
| Moves a process into a process group of its session, as setpgid() does. | |
| void | pgrp_release (struct pgroup *pgrp) |
| Frees a process group if no process is left in it, and its session if that was the session's last group. | |
Variables | |
| struct queue * | procs = QUEUE_NEW() |
| struct proc * | initproc |
| struct queue * | sessions = QUEUE_NEW() |
| struct bitmap * | pid_bitmap = BITMAP_NEW(4096) |
| static int | last_pid |
Processes: making them and ending them, their IDs, their descriptors, and their sessions and process groups.
A process that ends becomes a zombie: it keeps its ID and its exit status until its parent waits for it (proc_reap()). Its children go to init. Sessions and process groups follow POSIX's job control: a group that would be left stopped with no one to continue it (an orphaned group) gets SIGHUP and SIGCONT. See docs/kernel/processes.md.
Definition in file proc.c.
Says whether a process group is orphaned (POSIX): none of its members has a parent in another group of the same session, so no one there would continue it once it stops.
Init doesn't count as such a parent, since it isn't a shell.
| pgrp | the process group |
| gone | a process on its way out, which doesn't count as a member or a parent; or NULL |
Definition at line 227 of file proc.c.
References initproc, proc::parent, proc::pgrp, pgrp_orphaned(), pgroup::procs, queue_for, pgroup::session, and proc::zombie.
Referenced by pgrp_orphaned(), pgrp_orphaned_hangup(), signal_take(), and tty_background().
Sends SIGHUP and SIGCONT to a process group that gone leaving makes orphaned, if one of its members is stopped: nothing else would continue them.
Definition at line 245 of file proc.c.
References proc::pgrp, pgrp_orphaned(), pgrp_orphaned_hangup(), pgroup::procs, queue_for, proc::running, signal_pgrp_send(), and proc::stopped.
Referenced by pgrp_orphaned_hangup(), and proc_kill().
Returns whether p's process group is another group of the same session as q's.
Definition at line 264 of file proc.c.
References proc::pgrp, pgrp_other_same_session(), and pgroup::session.
Referenced by pgrp_other_same_session(), and proc_kill().
| void pgrp_release | ( | struct pgroup * | pgrp | ) |
Frees a process group if no process is left in it, and its session if that was the session's last group.
A terminal whose foreground group or session it was loses it.
| pgrp | the process group |
Definition at line 742 of file proc.c.
References queue::count, session::ctty, tty::fg, kfree(), NULL, session::pgps, pgrp_release(), pgroup::procs, pgroup::session, tty::session, and pgroup::session_node.
Referenced by pgrp_release(), proc_reap(), proc_setpgid(), and sys_setsid().
|
static |
Returns whether a process group or a session has pid as its ID.
Such an ID isn't given to a new process (POSIX), since groups and sessions outlive their leader.
Definition at line 56 of file proc.c.
References pgroup::pgid, session::pgps, pid_is_group(), queue_for, sessions, and session::sid.
Referenced by pid_is_group(), and proc_pid_alloc().
| int proc_fd_close | ( | struct proc * | proc, |
| int | fd ) |
Closes a descriptor: it is free again, and its reference to the open file is dropped.
Dropping the last reference closes the file.
| proc | the process |
| fd | the descriptor |
Definition at line 578 of file proc.c.
References proc::fds, file_put(), proc_fd_close(), and proc_fd_file().
Referenced by proc_execve(), proc_fd_close(), proc_fork(), proc_kill(), sys_accept(), sys_close(), and sys_pipe().
Finds the open file a descriptor refers to.
| proc | the process |
| fd | the descriptor |
Definition at line 560 of file proc.c.
References FD_RESERVED, proc::fds, FDS_COUNT, fd::file, NULL, and proc_fd_file().
Referenced by copy_fds(), fd_file(), fd_peek(), proc_execve(), proc_fd_close(), and proc_fd_file().
| int proc_fd_get | ( | struct proc * | proc | ) |
Reserves the lowest free descriptor of a process, while a system call sets it up: no other thread takes it, and it doesn't refer to a file yet.
proc_fd_install() or proc_fd_release() ends the reservation.
| proc | the process |
Definition at line 514 of file proc.c.
References FD_RESERVED, proc::fds, FDS_COUNT, fd::file, and proc_fd_get().
Referenced by do_openat(), proc_fd_get(), sys_accept(), sys_pipe(), and sys_socket().
Makes a reserved descriptor refer to an open file.
The caller's reference to the file becomes the descriptor's.
| proc | the process |
| fd | the descriptor, reserved by proc_fd_get() |
| file | the open file |
| flags | the descriptor's flags (FD_CLOEXEC) |
Definition at line 547 of file proc.c.
References proc::fds, fd::file, fd::flags, file::flags, and proc_fd_install().
Referenced by do_openat(), proc_fd_install(), sys_accept(), sys_fcntl(), sys_pipe(), and sys_socket().
| void proc_fd_release | ( | struct proc * | proc, |
| int | fd ) |
Frees a reserved descriptor that wasn't set up after all.
| proc | the process |
| fd | the descriptor |
Definition at line 532 of file proc.c.
References proc::fds, FDS_COUNT, and proc_fd_release().
Referenced by do_openat(), proc_fd_release(), sys_accept(), sys_pipe(), and sys_socket().
| int proc_init | ( | struct proc * | proc | ) |
Gives a new process (init) its ID and its descriptor table.
| proc | the process |
Definition at line 197 of file proc.c.
References proc::fds, FDS_COUNT, kmalloc(), M_ZERO, proc::pid, proc_init(), proc_pid_alloc(), and proc_pid_free().
Referenced by proc_dump(), proc_init(), and sched_init_spawn().
| void proc_kill | ( | struct proc * | proc | ) |
Ends a process: its threads end, its descriptors are closed, its memory is freed, its children go to init, and it becomes a zombie that its parent may wait for.
If the current thread is the process's, it doesn't return. Ending init restarts the machine.
| proc | the process; its exit status is set already |
Definition at line 375 of file proc.c.
References arch_cur_thread_kill(), arch_interrupts_disable(), arch_reboot(), session::ctty, curthread, proc::cwd, proc::exit, proc::fds, FDS_COUNT, queue::head, initproc, kfree(), kvm_space, session::leader, qnode::next, NULL, panic, proc::parent, proc::pgrp, pgrp_orphaned_hangup(), pgrp_other_same_session(), proc::pid, vm_space::pmap, pmap_decref(), printk(), proc_fd_close(), proc_kill(), proc_threads_end(), proc_zombie_notify(), procs, proc::running, sched_alarm(), pgroup::session, proc::sig_pending, thread_files_release(), proc::threads, tty_hangup(), qnode::value, vfs_close(), proc::vm_space, vm_space_destroy(), and proc::zombie.
Referenced by proc_execve(), proc_kill(), signal_exit(), and sys_exit().
| int proc_new | ( | struct proc ** | ref | ) |
Makes a new process structure, with one thread and an empty address space, on the list of every process.
It has no ID yet.
| ref | if not NULL, set to the new process |
Definition at line 114 of file proc.c.
References kfree(), kmalloc(), M_ZERO, NULL, vm_space::pmap, pmap_create(), pmap_decref(), proc_new(), procs, pmap::ref, proc::running, SIG_DFL, SIG_MAX, proc::sigaction, thread_new(), proc::threads, and proc::vm_space.
Referenced by kmain(), proc_fork(), and proc_new().
| int proc_pid_alloc | ( | void | ) |
Allocates a process ID, from 1 (init's) on.
Definition at line 80 of file proc.c.
References last_pid, bitmap::max_idx, pid_bitmap, pid_is_group(), and proc_pid_alloc().
Referenced by proc_fork(), proc_init(), and proc_pid_alloc().
Finds a process by its ID.
| pid | the ID |
Definition at line 179 of file proc.c.
References NULL, proc::pid, proc_pid_find(), procs, and queue_for.
Referenced by kernel_ctrlaltdel(), proc_alive(), proc_pid_find(), procfs_proc_maps(), procfs_proc_status(), procfs_proc_vmstats(), signal_send(), sys_setpgid(), and vt_signal().
| void proc_pid_free | ( | int | pid | ) |
Frees a process ID.
| pid | the ID |
Definition at line 102 of file proc.c.
References pid_bitmap, and proc_pid_free().
Referenced by proc_fork(), proc_init(), proc_pid_free(), and proc_reap().
| int proc_reap | ( | struct proc * | proc | ) |
Frees a zombie, once its parent waited for it (or doesn't wait for its children).
Its CPU times are added to its parent's children's times.
| proc | the zombie |
Definition at line 484 of file proc.c.
References proc::cstime, proc::cutime, kfree(), proc::name, proc::parent, proc::pgrp, proc::pgrp_node, pgrp_release(), proc::pid, proc_pid_free(), proc_reap(), pgroup::procs, procs, proc::stime, and proc::utime.
Referenced by proc_reap(), proc_zombie_notify(), and sys_waitpid().
Moves a process into a process group of its session, as setpgid() does.
A group can only be joined if it exists and has members; a process can only start a new group with its own ID as the group's ID.
| proc | the process |
| pgid | the group's ID |
Definition at line 667 of file proc.c.
References queue::count, kfree(), kmalloc(), pgroup::leader, M_ZERO, NULL, pgroup::pgid, session::pgps, proc::pgrp, proc::pgrp_node, pgrp_release(), proc::pid, proc_setpgid(), pgroup::procs, queue_for, pgroup::session, and pgroup::session_node.
Referenced by proc_setpgid(), and sys_setpgid().
Ends the threads of a process, but one.
A thread that isn't running is freed. One running on another CPU (in user mode, since this CPU has the kernel lock) is marked killed and made to enter the kernel now, where it frees itself.
| proc | the process |
| keep | the thread to keep, or NULL |
| exiting | whether the process is ending: then the threads running elsewhere are detached from it at once; otherwise they leave its list when they go, and wake up proc->thread_join |
Definition at line 305 of file proc.c.
References queue::head, kfree(), thread::killed, NULL, thread::owner, proc_threads_end(), thread::run_link, sched_thread_cpu(), sched_thread_kick(), sched_timer_cancel(), thread::state, thread_files_release(), thread_kill(), proc::threads, thread::waitq, and ZOMBIE.
Referenced by proc_kill(), proc_threads_end(), and proc_threads_exec().
| void proc_threads_exec | ( | struct proc * | proc | ) |
Ends every thread of a process but the current one, for execve() (POSIX: they run in the program that is replaced).
It waits for the threads running on other CPUs to be gone.
| proc | the process, which must be the current thread's |
Definition at line 358 of file proc.c.
References curthread, proc_threads_end(), proc_threads_exec(), proc::thread_join, and waitq_sleep_unint().
Referenced by binfmt_fmt_load(), and proc_threads_exec().
|
static |
Tells a zombie's parent that it ended: its wait() wakes up and it gets SIGCHLD.
If the parent doesn't wait for its children (it ignores SIGCHLD, or set SA_NOCLDWAIT), the zombie is reaped at once.
Definition at line 272 of file proc.c.
References proc::parent, proc_reap(), proc_zombie_notify(), SIG_IGN, proc::sigaction, signal_proc_send(), proc::wait_queue, and waitq_wakeup().
Referenced by proc_kill(), and proc_zombie_notify().
| int session_new | ( | struct proc * | proc | ) |
Makes a new session, with a new process group, both led by a process and with its ID, and moves the process into it, as setsid() does.
| proc | the process |
Definition at line 596 of file proc.c.
References kfree(), kmalloc(), pgroup::leader, session::leader, M_ZERO, NULL, pgroup::pgid, session::pgps, proc::pgrp, proc::pgrp_node, proc::pid, pgroup::procs, pgroup::session, session_new(), pgroup::session_node, and session::sid.
Referenced by kproc_init(), sched_init_spawn(), session_new(), and sys_setsid().
| struct proc* initproc |
Definition at line 39 of file proc.c.
Referenced by kmain(), pgrp_orphaned(), and proc_kill().
|
static |
Definition at line 51 of file proc.c.
Referenced by proc_pid_alloc().
| struct bitmap* pid_bitmap = BITMAP_NEW(4096) |
Definition at line 45 of file proc.c.
Referenced by proc_pid_alloc(), and proc_pid_free().
Definition at line 37 of file proc.c.
Referenced by kproc_init(), proc_fork(), proc_kill(), proc_new(), proc_pid_find(), proc_reap(), procfs_finddir(), procfs_readdir(), signal_send(), and sys_waitpid().
Definition at line 42 of file proc.c.
Referenced by pid_is_group().