Thread (9 messages) 9 messages, 4 authors, 2005-06-01

Re: [PATCH] Don't explode on swsusp failure to find swap

From: Pavel Machek <hidden>
Date: 2005-06-01 09:33:47
Also in: lkml
Subsystem: hibernation (aka software suspend, aka swsusp), suspend to ram, the rest · Maintainers: "Rafael J. Wysocki", Linus Torvalds

Hi!
quoted
quoted
quoted
If we specify a swap device for swsusp using resume= kernel argument and
that device doesn't exist in the swap list, we end up calling
swsusp_free() before we have allocated pagedir_save. That causes us to
explode when trying to free it.

Pavel, does that look right ?
It looks like a workaround. We should not call swsusp_free in case
device does not exists. Quick look did not reveal where the bug comes
from, can you try to trace it?
								Pavel
Well, the bug comes from arch code calling swsusp_save() which fails,
then we call swsusp_free()
More specifically, arch suspend calls swsusp_save().

It fails and returns the error to the arch asm code, which itself
returns it to it's caller swsusp_suspend(), which does that:

 	if ((error = swsusp_arch_suspend()))
		swsusp_free();
Ugh, swsusp_free should be totally unneccessary at this point; only
error returns are from the time before anything is allocated.

Does something like this help?
diff --git a/kernel/power/swsusp.c b/kernel/power/swsusp.c
--- a/kernel/power/swsusp.c
+++ b/kernel/power/swsusp.c
@@ -975,13 +975,6 @@ extern asmlinkage int swsusp_arch_resume
 
 asmlinkage int swsusp_save(void)
 {
-	int error = 0;
-
-	if ((error = swsusp_swap_check())) {
-		printk(KERN_ERR "swsusp: FATAL: cannot find swap device, try "
-				"swapon -a!\n");
-		return error;
-	}
 	return suspend_prepare_image();
 }
 
@@ -999,12 +992,19 @@ int swsusp_suspend(void)
 	 */
 	if ((error = device_power_down(PMSG_FREEZE))) {
 		local_irq_enable();
-		swsusp_free();
 		return error;
 	}
+
+	if ((error = swsusp_swap_check())) {
+		printk(KERN_ERR "swsusp: FATAL: cannot find swap device, try "
+				"swapon -a!\n");
+		local_irq_enable();
+		return error;
+	}
+
 	save_processor_state();
 	if ((error = swsusp_arch_suspend()))
-		swsusp_free();
+		printk("Error %d suspending\n", error);
 	/* Restore control flow magically appears here */
 	restore_processor_state();
 	BUG_ON (nr_copy_pages_check != nr_copy_pages);

Attachments

Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help