⬢ DragonFlyBSD Kernel Audit
DF-3225 / fix.diff
← back to finding ↓ download raw
--- a/sys/vfs/procfs/procfs_ctl.c
+++ b/sys/vfs/procfs/procfs_ctl.c
@@ -141,6 +141,22 @@
 			return (EINVAL);
 
 		/*
+		 * Refuse to create a tracer cycle (mirrors the
+		 * PT_ATTACH ancestor check in kern/sys_process.c).
+		 * Without this two cooperating processes can attach
+		 * each other and build a p_pptr cycle; the unbounded
+		 * ancestor walk in sys_process.c then livelocks the
+		 * kernel forever while holding the target's p_token.
+		 */
+		if (curp->p_flags & P_TRACED) {
+			struct proc *pp;
+
+			for (pp = curp->p_pptr; pp != NULL; pp = pp->p_pptr)
+				if (pp == p)
+					return (EINVAL);
+		}
+
+		/*
 		 * Go ahead and set the trace flag.
 		 * Save the old parent (it's reset in
 		 *   _DETACH, and also in kern_exit.c:wait4()