svn commit: r303606 - stable/11/sys/kern
Konstantin Belousov
kib at FreeBSD.org
Mon Aug 1 06:34:56 UTC 2016
Author: kib
Date: Mon Aug 1 06:34:55 2016
New Revision: 303606
URL: https://svnweb.freebsd.org/changeset/base/303606
Log:
MFC r302614:
Revive the check, disabled in r197963.
MFC r302999:
On first exec after vfork(), call signotify() to handle pending
reenabled signals.
Approved by: re (delphij)
Modified:
stable/11/sys/kern/kern_exec.c
stable/11/sys/kern/subr_trap.c
Directory Properties:
stable/11/ (props changed)
Modified: stable/11/sys/kern/kern_exec.c
==============================================================================
--- stable/11/sys/kern/kern_exec.c Mon Aug 1 05:09:11 2016 (r303605)
+++ stable/11/sys/kern/kern_exec.c Mon Aug 1 06:34:55 2016 (r303606)
@@ -759,6 +759,8 @@ interpret:
if (p->p_flag & P_PPWAIT) {
p->p_flag &= ~(P_PPWAIT | P_PPTRACE);
cv_broadcast(&p->p_pwait);
+ /* STOPs are no longer ignored, arrange for AST */
+ signotify(td);
}
/*
Modified: stable/11/sys/kern/subr_trap.c
==============================================================================
--- stable/11/sys/kern/subr_trap.c Mon Aug 1 05:09:11 2016 (r303605)
+++ stable/11/sys/kern/subr_trap.c Mon Aug 1 06:34:55 2016 (r303606)
@@ -101,17 +101,29 @@ userret(struct thread *td, struct trapfr
td->td_name);
KASSERT((p->p_flag & P_WEXIT) == 0,
("Exiting process returns to usermode"));
-#if 0
#ifdef DIAGNOSTIC
- /* Check that we called signotify() enough. */
- PROC_LOCK(p);
- thread_lock(td);
- if (SIGPENDING(td) && ((td->td_flags & TDF_NEEDSIGCHK) == 0 ||
- (td->td_flags & TDF_ASTPENDING) == 0))
- printf("failed to set signal flags properly for ast()\n");
- thread_unlock(td);
- PROC_UNLOCK(p);
-#endif
+ /*
+ * Check that we called signotify() enough. For
+ * multi-threaded processes, where signal distribution might
+ * change due to other threads changing sigmask, the check is
+ * racy and cannot be performed reliably.
+ * If current process is vfork child, indicated by P_PPWAIT, then
+ * issignal() ignores stops, so we block the check to avoid
+ * classifying pending signals.
+ */
+ if (p->p_numthreads == 1) {
+ PROC_LOCK(p);
+ thread_lock(td);
+ if ((p->p_flag & P_PPWAIT) == 0) {
+ KASSERT(!SIGPENDING(td) || (td->td_flags &
+ (TDF_NEEDSIGCHK | TDF_ASTPENDING)) ==
+ (TDF_NEEDSIGCHK | TDF_ASTPENDING),
+ ("failed to set signal flags for ast p %p "
+ "td %p fl %x", p, td, td->td_flags));
+ }
+ thread_unlock(td);
+ PROC_UNLOCK(p);
+ }
#endif
#ifdef KTRACE
KTRUSERRET(td);
@@ -265,6 +277,29 @@ ast(struct trapframe *framep)
#endif
}
+#ifdef DIAGNOSTIC
+ if (p->p_numthreads == 1 && (flags & TDF_NEEDSIGCHK) == 0) {
+ PROC_LOCK(p);
+ thread_lock(td);
+ /*
+ * Note that TDF_NEEDSIGCHK should be re-read from
+ * td_flags, since signal might have been delivered
+ * after we cleared td_flags above. This is one of
+ * the reason for looping check for AST condition.
+ * See comment in userret() about P_PPWAIT.
+ */
+ if ((p->p_flag & P_PPWAIT) == 0) {
+ KASSERT(!SIGPENDING(td) || (td->td_flags &
+ (TDF_NEEDSIGCHK | TDF_ASTPENDING)) ==
+ (TDF_NEEDSIGCHK | TDF_ASTPENDING),
+ ("failed2 to set signal flags for ast p %p td %p "
+ "fl %x %x", p, td, flags, td->td_flags));
+ }
+ thread_unlock(td);
+ PROC_UNLOCK(p);
+ }
+#endif
+
/*
* Check for signals. Unlocked reads of p_pendingcnt or
* p_siglist might cause process-directed signal to be handled
More information about the svn-src-stable
mailing list