diff --git a/include/linux/lsm_hook_defs.h b/include/linux/lsm_hook_defs.h
index 04c01794de83..e28468e84300 100644
--- a/include/linux/lsm_hook_defs.h
+++ b/include/linux/lsm_hook_defs.h
@@ -225,6 +225,7 @@ LSM_HOOK(int, -ENOSYS, task_prctl, int option, unsigned long arg2,
unsigned long arg3, unsigned long arg4, unsigned long arg5)
LSM_HOOK(void, LSM_RET_VOID, task_to_inode, struct task_struct *p,
struct inode *inode)
+LSM_HOOK(void, LSM_RET_VOID, task_fatal_signal, const kernel_siginfo_t *siginfo)
LSM_HOOK(int, 0, ipc_permission, struct kern_ipc_perm *ipcp, short flag)
LSM_HOOK(void, LSM_RET_VOID, ipc_getsecid, struct kern_ipc_perm *ipcp,
u32 *secid)
diff --git a/include/linux/lsm_hooks.h b/include/linux/lsm_hooks.h
index 5c4c5c0602cb..fc8bef0f15d9 100644
--- a/include/linux/lsm_hooks.h
+++ b/include/linux/lsm_hooks.h
@@ -799,6 +799,10 @@
* security attributes, e.g. for /proc/pid inodes.
* @p contains the task_struct for the task.
* @inode contains the inode structure for the inode.
+ * @task_fatal_signal:
+ * This hook allows security modules to be notified when a task gets a
+ * fatal signal.
+ * @siginfo contains the signal information.
*
* Security hooks for Netlink messaging.
*
diff --git a/include/linux/security.h b/include/linux/security.h
index 06f7c50ce77f..609c76c6c764 100644
--- a/include/linux/security.h
+++ b/include/linux/security.h
@@ -433,6 +433,7 @@ int security_task_kill(struct task_struct *p, struct kernel_siginfo *info,
int security_task_prctl(int option, unsigned long arg2, unsigned long arg3,
unsigned long arg4, unsigned long arg5);
void security_task_to_inode(struct task_struct *p, struct inode *inode);
+void security_task_fatal_signal(const kernel_siginfo_t *siginfo);
int security_ipc_permission(struct kern_ipc_perm *ipcp, short flag);
void security_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid);
int security_msg_msg_alloc(struct msg_msg *msg);
@@ -1183,6 +1184,9 @@ static inline int security_task_prctl(int option, unsigned long arg2,
static inline void security_task_to_inode(struct task_struct *p, struct inode *inode)
{ }
+static inline void security_task_fatal_signal(const kernel_siginfo_t *siginfo)
+{ }
+
static inline int security_ipc_permission(struct kern_ipc_perm *ipcp,
short flag)
{diff --git a/kernel/signal.c b/kernel/signal.c
index f7c6ffcbd044..4380763b3d8d 100644
--- a/kernel/signal.c
+++ b/kernel/signal.c
@@ -2804,6 +2804,7 @@ bool get_signal(struct ksignal *ksig)
/*
* Anything else is fatal, maybe with a core dump.
*/
+ security_task_fatal_signal(&ksig->info);
current->flags |= PF_SIGNALED;
if (sig_kernel_coredump(signr)) {diff --git a/security/security.c b/security/security.c
index b38155b2de83..208e3e7d4284 100644
--- a/security/security.c
+++ b/security/security.c
@@ -1891,6 +1891,11 @@ void security_task_to_inode(struct task_struct *p, struct inode *inode)
call_void_hook(task_to_inode, p, inode);
}
+void security_task_fatal_signal(const kernel_siginfo_t *siginfo)
+{
+ call_void_hook(task_fatal_signal, siginfo);
+}
+
int security_ipc_permission(struct kern_ipc_perm *ipcp, short flag)
{
return call_int_hook(ipc_permission, 0, ipcp, flag);
--