<html><head><meta name="color-scheme" content="light dark"></head><body><pre style="word-wrap: break-word; white-space: pre-wrap;">
From: Pavel Machek &lt;pavel@ucw.cz&gt;

If process freezing fails, some processes are frozen, and rest are left in
"were asked to be frozen" state.  Thats wrong, we should leave it in some
consistent state.

Signed-off-by: Pavel Machek &lt;pavel@suse.cz&gt;
Signed-off-by: Andrew Morton &lt;akpm@osdl.org&gt;
---

 kernel/power/process.c |   24 ++++++++++++++++++++++--
 1 files changed, 22 insertions(+), 2 deletions(-)

diff -puN kernel/power/process.c~pm-fix-process-freezing kernel/power/process.c
--- 25/kernel/power/process.c~pm-fix-process-freezing	Mon Aug 29 15:38:51 2005
+++ 25-akpm/kernel/power/process.c	Mon Aug 29 15:38:51 2005
@@ -81,13 +81,33 @@ int freeze_processes(void)
 		} while_each_thread(g, p);
 		read_unlock(&amp;tasklist_lock);
 		yield();			/* Yield is okay here */
-		if (time_after(jiffies, start_time + TIMEOUT)) {
+		if (todo &amp;&amp; time_after(jiffies, start_time + TIMEOUT)) {
 			printk( "\n" );
 			printk(KERN_ERR " stopping tasks failed (%d tasks remaining)\n", todo );
-			return todo;
+			break;
 		}
 	} while(todo);
 
+	/* This does not unfreeze processes that are already frozen
+	 * (we have slightly ugly calling convention in that respect,
+	 * and caller must call thaw_processes() if something fails),
+	 * but it cleans up leftover PF_FREEZE requests.
+	 */
+	if (todo) {
+		read_lock(&amp;tasklist_lock);
+		do_each_thread(g, p)
+			if (freezing(p)) {
+				pr_debug("  clean up: %s\n", p-&gt;comm);
+				p-&gt;flags &amp;= ~PF_FREEZE;
+				spin_lock_irqsave(&amp;p-&gt;sighand-&gt;siglock, flags);
+				recalc_sigpending_tsk(p);
+				spin_unlock_irqrestore(&amp;p-&gt;sighand-&gt;siglock, flags);
+			}
+		while_each_thread(g, p);
+		read_unlock(&amp;tasklist_lock);
+		return todo;
+	}
+
 	printk( "|\n" );
 	BUG_ON(in_atomic());
 	return 0;
_
</pre></body></html>