On top of signal-remove-the-wrong-signal_pending-check-in-restore_user_sigmask.patch Let me repeat, every file touched by this patch needs more cleanups, fs/aio.c looks wrong with or without the recent changes. Lets discuss this later. To simplify the review, please see the code with this patch applied. I am using epoll_pwait() as an example because it looks very simple. Note that this patch moves WARN_ON(!TIF_SIGPENDING) from set_restore_sigmask() to restore_unless(). int set_user_sigmask(const sigset_t __user *umask, size_t sigsetsize) { sigset_t *kmask; if (!umask) return 0; if (sigsetsize != sizeof(sigset_t)) return -EINVAL; if (copy_from_user(kmask, umask, sizeof(sigset_t))) return -EFAULT; set_restore_sigmask(); current->saved_sigmask = current->blocked; set_current_blocked(kmask); return 0; } static inline void restore_saved_sigmask_unless(bool interrupted) { if (interrupted) WARN_ON(!test_thread_flag(TIF_SIGPENDING)); else restore_saved_sigmask(); } SYSCALL_DEFINE6(epoll_pwait, int, epfd, struct epoll_event __user *, events, int, maxevents, int, timeout, const sigset_t __user *, sigmask, size_t, sigsetsize) { int error; /* * If the caller wants a certain signal mask to be set during the wait, * we apply it here. */ error = set_user_sigmask(sigmask, sigsetsize); if (error) return error; error = do_epoll_wait(epfd, events, maxevents, timeout); restore_saved_sigmask_unless(error == -EINTR); return error; } Oleg.