kernel/signal.c
Source file repositories/reference/linux-study-clean/kernel/signal.c
File Facts
- System
- Linux kernel
- Corpus path
kernel/signal.c- Extension
.c- Size
- 134578 bytes
- Lines
- 5055
- Domain
- Core OS
- Bucket
- Scheduler, Processes, Timers, Sync, And Syscalls
- Inferred role
- Core OS: syscall or user/kernel boundary
- Status
- core implementation candidate
Why This File Exists
Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.
- Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.
- Defines or participates in a user/kernel boundary; inspect argument validation, copy_from_user/copy_to_user, credentials, and dispatch target.
- Touches user memory; correctness depends on fault-safe copying and privilege boundary handling.
- Uses kernel synchronization; read lock ordering, sleepability, and interrupt context assumptions before translating.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/slab.hlinux/export.hlinux/init.hlinux/sched/mm.hlinux/sched/user.hlinux/sched/debug.hlinux/sched/task.hlinux/sched/task_stack.hlinux/sched/cputime.hlinux/file.hlinux/fs.hlinux/mm.hlinux/proc_fs.hlinux/tty.hlinux/binfmts.hlinux/coredump.hlinux/security.hlinux/syscalls.hlinux/ptrace.hlinux/signal.hlinux/signalfd.hlinux/ratelimit.hlinux/task_work.hlinux/capability.hlinux/freezer.hlinux/pid_namespace.hlinux/nsproxy.hlinux/user_namespace.hlinux/uprobes.hlinux/compat.hlinux/cn_proc.hlinux/compiler.h
Detected Declarations
syscall restart_syscallsyscall rt_sigprocmasksyscall rt_sigpendingsyscall rt_sigtimedwaitsyscall rt_sigtimedwait_time32syscall killsyscall pidfd_send_signalsyscall tgkillsyscall tkillsyscall rt_sigqueueinfosyscall rt_tgsigqueueinfosyscall sigaltstacksyscall sigpendingsyscall sigprocmasksyscall rt_sigactionsyscall sigactionsyscall sgetmasksyscall ssetmasksyscall signalsyscall pausesyscall rt_sigsuspendsyscall sigsuspendsyscall sigsuspendenum sig_handlerfunction sig_handler_ignoredfunction sig_task_ignoredfunction sig_ignoredfunction has_pending_signalsfunction recalc_sigpending_tskfunction recalc_sigpendingfunction calculate_sigpendingfunction sigmaskfunction print_dropped_signalfunction task_set_jobctl_pendingfunction task_clear_jobctl_trappingfunction task_clear_jobctl_trappingfunction task_participate_group_stopfunction task_join_group_stopfunction __sigqueue_initfunction __sigqueue_freefunction flush_sigqueuefunction flush_signalsfunction ignore_signalsfunction flush_signal_handlersfunction unhandled_signalfunction collect_signalfunction __dequeue_signalfunction dequeue_signal
Annotated Snippet
SYSCALL_DEFINE0(restart_syscall)
{
struct restart_block *restart = ¤t->restart_block;
return restart->fn(restart);
}
long do_no_restart_syscall(struct restart_block *param)
{
return -EINTR;
}
static void __set_task_blocked(struct task_struct *tsk, const sigset_t *newset)
{
if (task_sigpending(tsk) && !thread_group_empty(tsk)) {
sigset_t newblocked;
/* A set of now blocked but previously unblocked signals. */
sigandnsets(&newblocked, newset, ¤t->blocked);
retarget_shared_pending(tsk, &newblocked);
}
tsk->blocked = *newset;
recalc_sigpending();
}
/**
* set_current_blocked - change current->blocked mask
* @newset: new mask
*
* It is wrong to change ->blocked directly, this helper should be used
* to ensure the process can't miss a shared signal we are going to block.
*/
void set_current_blocked(sigset_t *newset)
{
sigdelsetmask(newset, sigmask(SIGKILL) | sigmask(SIGSTOP));
__set_current_blocked(newset);
}
void __set_current_blocked(const sigset_t *newset)
{
struct task_struct *tsk = current;
/*
* In case the signal mask hasn't changed, there is nothing we need
* to do. The current->blocked shouldn't be modified by other task.
*/
if (sigequalsets(&tsk->blocked, newset))
return;
spin_lock_irq(&tsk->sighand->siglock);
__set_task_blocked(tsk, newset);
spin_unlock_irq(&tsk->sighand->siglock);
}
/*
* This is also useful for kernel threads that want to temporarily
* (or permanently) block certain signals.
*
* NOTE! Unlike the user-mode sys_sigprocmask(), the kernel
* interface happily blocks "unblockable" signals like SIGKILL
* and friends.
*/
int sigprocmask(int how, sigset_t *set, sigset_t *oldset)
{
struct task_struct *tsk = current;
sigset_t newset;
/* Lockless, only current can change ->blocked, never from irq */
if (oldset)
*oldset = tsk->blocked;
switch (how) {
case SIG_BLOCK:
sigorsets(&newset, &tsk->blocked, set);
break;
case SIG_UNBLOCK:
sigandnsets(&newset, &tsk->blocked, set);
break;
case SIG_SETMASK:
newset = *set;
break;
default:
return -EINVAL;
}
__set_current_blocked(&newset);
return 0;
}
EXPORT_SYMBOL(sigprocmask);
/*
* The api helps set app-provided sigmasks.
Annotation
- Immediate include surface: `linux/slab.h`, `linux/export.h`, `linux/init.h`, `linux/sched/mm.h`, `linux/sched/user.h`, `linux/sched/debug.h`, `linux/sched/task.h`, `linux/sched/task_stack.h`.
- Detected declarations: `syscall restart_syscall`, `syscall rt_sigprocmask`, `syscall rt_sigpending`, `syscall rt_sigtimedwait`, `syscall rt_sigtimedwait_time32`, `syscall kill`, `syscall pidfd_send_signal`, `syscall tgkill`, `syscall tkill`, `syscall rt_sigqueueinfo`.
- Atlas domain: Core OS / Scheduler, Processes, Timers, Sync, And Syscalls.
- Implementation status: core implementation candidate.
- This snippet crosses the user/kernel memory boundary; validate fault handling and access checks before translating the pattern.
- Synchronization appears in or near this file; preserve lock ordering, sleepability, and interrupt-context constraints.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.