return (sig < SIGRTMIN) && sigismember(&signals->signal, sig);
 }
 
-#ifdef CONFIG_USER_NS
-static inline void userns_fixup_signal_uid(struct kernel_siginfo *info, struct task_struct *t)
-{
-       if (current_user_ns() == task_cred_xxx(t, user_ns))
-               return;
-
-       if (SI_FROMKERNEL(info))
-               return;
-
-       rcu_read_lock();
-       info->si_uid = from_kuid_munged(task_cred_xxx(t, user_ns),
-                                       make_kuid(current_user_ns(), info->si_uid));
-       rcu_read_unlock();
-}
-#else
-static inline void userns_fixup_signal_uid(struct kernel_siginfo *info, struct task_struct *t)
-{
-       return;
-}
-#endif
-
 static int __send_signal(int sig, struct kernel_siginfo *info, struct task_struct *t,
                        enum pid_type type, int from_ancestor_ns)
 {
                        q->info.si_code = SI_USER;
                        q->info.si_pid = task_tgid_nr_ns(current,
                                                        task_active_pid_ns(t));
-                       q->info.si_uid = from_kuid_munged(current_user_ns(), current_uid());
+                       rcu_read_lock();
+                       q->info.si_uid =
+                               from_kuid_munged(task_cred_xxx(t, user_ns),
+                                                current_uid());
+                       rcu_read_unlock();
                        break;
                case (unsigned long) SEND_SIG_PRIV:
                        clear_siginfo(&q->info);
                        break;
                default:
                        copy_siginfo(&q->info, info);
-                       if (from_ancestor_ns)
-                               q->info.si_pid = 0;
                        break;
                }
-
-               userns_fixup_signal_uid(&q->info, t);
-
        } else if (!is_si_special(info)) {
                if (sig >= SIGRTMIN && info->si_code != SI_USER) {
                        /*
        return ret;
 }
 
+static inline bool has_si_pid_and_uid(struct kernel_siginfo *info)
+{
+       bool ret = false;
+       switch (siginfo_layout(info->si_signo, info->si_code)) {
+       case SIL_KILL:
+       case SIL_CHLD:
+       case SIL_RT:
+               ret = true;
+               break;
+       case SIL_TIMER:
+       case SIL_POLL:
+       case SIL_FAULT:
+       case SIL_FAULT_MCEERR:
+       case SIL_FAULT_BNDERR:
+       case SIL_FAULT_PKUERR:
+       case SIL_SYS:
+               ret = false;
+               break;
+       }
+       return ret;
+}
+
 static int send_signal(int sig, struct kernel_siginfo *info, struct task_struct *t,
                        enum pid_type type)
 {
        from_ancestor_ns = si_fromuser(info) &&
                           !task_pid_nr_ns(current, task_active_pid_ns(t));
 #endif
+       if (!is_si_special(info) && has_si_pid_and_uid(info)) {
+               struct user_namespace *t_user_ns;
 
+               rcu_read_lock();
+               t_user_ns = task_cred_xxx(t, user_ns);
+               if (current_user_ns() != t_user_ns) {
+                       kuid_t uid = make_kuid(current_user_ns(), info->si_uid);
+                       info->si_uid = from_kuid_munged(t_user_ns, uid);
+               }
+               rcu_read_unlock();
+
+               if (!task_pid_nr_ns(current, task_active_pid_ns(t)))
+                       info->si_pid = 0;
+       }
        return __send_signal(sig, info, t, type, from_ancestor_ns);
 }