Skip to contentSkip to conversation

swsusp doesn't suspend devices

PATCH Pierre Ossman 3 participants 5 messages Sep 7, 2005

Subsystems (2)
lore
Share & tools
lore
#0 lore raw

It would seem that swsusp doesn't properly suspend devices, or more precisely it wakes them up again before suspending the machine.

The problem is in swsusp_suspend(). It is designed as if swsusp_arch_suspend() would suspend the hardware, when in fact all it does is prepare for a suspend. The effect is that devices are brought back up because swsusp_suspend() believes it is resuming.

Below is a patch that uses the same system as kernel/power/disk.c to determine if it's suspending or resuming. The patch brings up a new problem though, disk writes generate a huge amount of "scheduling while atomic".

---

kernel/power/swsusp.c (working copy) renamed from kernel/power/swsusp.c (revision 165) +11 -6
Index: linux-wbsd/kernel/power/swsusp.c
===================================================================
@@ -84,6 +84,8 @@
 /* Local variables that should not be affected by save */
 static unsigned int nr_copy_pages __nosavedata = 0;
 
+static int in_suspend __nosavedata = 0;
+
 /* Suspend pagedir is allocated before final copy, therefore it
    must be freed after resume
 
@@ -897,15 +899,18 @@
                return error;
        }
 
+       in_suspend = 1;
        save_processor_state();
        if ((error = swsusp_arch_suspend()))
                printk("Error %d suspending\n", error);
-       /* Restore control flow magically appears here */
-       restore_processor_state();
-       BUG_ON (nr_copy_pages_check != nr_copy_pages);
-       restore_highmem();
-       device_power_up();
-       local_irq_enable();
+       if (!in_suspend || error) {
+               /* Restore control flow magically appears here */
+               restore_processor_state();
+               BUG_ON (nr_copy_pages_check != nr_copy_pages);
+               restore_highmem();
+               device_power_up();
+               local_irq_enable();
+       }
        return error;
 }
 
#1 lore raw
Quoted 2 lines · Pierre Ossman

It would seem that swsusp doesn't properly suspend devices, or more precisely it wakes them up again before suspending the machine.

Yes, it does. By design.

Greetings,
Rafael

Signature · 3 lines
- Would you tell me, please, which way I ought to go from here?
- That depends a good deal on where you want to get to.
		-- Lewis Carroll "Alice's Adventures in Wonderland"
#2 lore raw
Quoted 12 lines · Rafael J. Wysocki
Quoted 4 lines · Pierre Ossman

It would seem that swsusp doesn't properly suspend devices, or more precisely it wakes them up again before suspending the machine.

Yes, it does. By design.

That seems counter-productive, so I'm obviously missing something.

#3 lore raw
Quoted 10 lines · Pierre Ossman
Quoted 8 lines · Rafael J. Wysocki
Quoted 4 lines · Pierre Ossman

It would seem that swsusp doesn't properly suspend devices, or more precisely it wakes them up again before suspending the machine.

Quoted 6 lines
Quoted 4 lines

Yes, it does. By design.

That seems counter-productive, so I'm obviously missing something.

In swsusp, the suspend consists of freezing processes, suspending devices, turning off interrupts, and creating a memory snapshot (the image) in that state (ie of the "frozen" system). Afterwards the image is in memory and it has to be written to a swap partition. For this purpose we need to resume some devices, in particular the disk that contains this swap partition, but it always relies on some other devices that have to be resumed as well. In principle we could check what devices have to be resumed, but currently we just resume them all. An additional upside of this approach is that the suspend and resume code is (almost) identical.

Greetings,
Rafael

Signature · 3 lines
- Would you tell me, please, which way I ought to go from here?
- That depends a good deal on where you want to get to.
		-- Lewis Carroll "Alice's Adventures in Wonderland"
#4 lore raw
In reply to Pierre Ossman

Hi!

Quoted 2 lines

It would seem that swsusp doesn't properly suspend devices, or more precisely it wakes them up again before suspending the machine.

Yes, and that's okay.

What happens to devices during swsusp? They seem to be resumed
during system suspend?

A: That's correct. We need to resume them if we want to write image to disk. Whole sequence goes like

Suspend part
~~~~~~~~~~~~
running system, user asks for suspend-to-disk

user processes are stopped

suspend(PMSG_FREEZE): devices are frozen so that they don't
interfere
with state snapshot

state snapshot: copy of whole used memory is taken with
interrupts disabled

resume(): devices are woken up so that we can write image to
swap

write image to swap

suspend(PMSG_SUSPEND): suspend devices so that we can power off

turn the power off

Resume part
~~~~~~~~~~~
(is actually pretty similar)

running system, user asks for suspend-to-disk

user processes are stopped (in common case there are none, but
with resume-from-initrd, noone k\nows)

read image from disk

suspend(PMSG_FREEZE): devices are frozen so that they don't
interfere
with image restoration

image restoration: rewrite memory with image

resume(): devices are woken up so that system can continue

thaw all user processes

Signature · 1 line
if you have sharp zaurus hardware you don't need... you know my address