Hibernation using systemctl and getting it working in tough cases
For me, pm-hibernate always fails. After some tweaks, I was able to hibernate using the interface of systemd (init system in 16.04 and above). I also managed to get it working on 17.04 with a swap file. This case study may be useful for others with problems.
First try:
sudo systemctl hibernate
If that fails, begin troubleshooting: in the hibernate state (HTD or ACPI S4) the machine state is written to disk so that no power is needed to preserve it. The state is written either to a swap partition or to a swap file. Note: if using Btrfs DO NOT attempt to use a swap file as this may cause filesystem corruption
Your swap partition or swap file may need to be the same size as RAM to allow hibernation, but there is a good chance you will be able to hibernate if it is at least 2/5 the size of RAM, according to the Arch wiki page, so try other steps first before increasing swap size.
If your problem is that you get a clean boot instead of the expected resume, at a minimum you most likely need to set a boot parameter to find the disk image
Find your swap partition:
grep swap /etc/fstab
for me this returns (partial output)
# swap was on /dev/mmcblk0p3 during installation
where /dev/mmcblk0p3 is the partition to specify
Add a boot parameter:
sudoedit /etc/default/grub
To the line starting GRUB_CMDLINE_LINUX_DEFAULT add resume=/dev/YourSwapPartition to the section in quotes (replace with the the partition you identified earlier). Using my example:
Any time you change this file, you must run sudo update-grub or the changes will have no effect.
Now you need to reboot. Then you can try to hibernate, by issuing the command:
sudo systemctl hibernate
To resume, press the power button and the system will boot.
If you still have problems, start debugging.
I include my case below as an example, but detailed information on debugging S states can be found in this blog and also this one.
Set some more boot parameters to capture more information. Remove quiet and splash and add initcall_debug and no_console_suspend which will cause init system calls to be printed to the console so you can watch what is going wrong. I set this:
Which helped me see what was going wrong on resume from hibernation. You can also try using dmesg.
In my case, after resume I lost WiFi, and the kernel clearly was upset as most commands (for example reading anything from /sys, reloading modules or any systemctl command) would not work - the process would appear to start and just hang (all this would be returned to normal after reboot of course). Watching the system very slowly shut down and reading all the debug messages, I noticed that there were a lot of problems with "brcm", so I guessed my Broadcom wireless driver module was to blame. Sure enough I adjusted my hibernation procedure to unload the module first:
And everything worked perfectly. I also have to blacklist the btsdio module which seems to be incompatible with brcmfmac
Update: Hibernation using a swap file on 17.04.
Once again with help from the Arch wiki page and some additional tinkering, I managed to get hibernation to work on 17.04 with a swap file. This required an additional boot parameter, resume_offset=n where n is the first number under physical_offset in the output of sudo filefrag -v /swapfile:
$ sudo filefrag -v /swapfile
Filesystem type is: ef53
File size of /swapfile is 1425873920 (348114 blocks of 4096 bytes)
ext: logical_offset: physical_offset: length: expected: flags:
0: 0.. 32767: 34816.. 67583: 32768:
1: 32768.. 63487: 67584.. 98303: 30720:
....
Therefore, the additional boot parameter in my case is resume_offset=34816. You still need to set a boot parameter for the partition to resume from. This will be the root partition (or whatever partition your swap file is located on) My parameters are now:
Where /dev/mmcblk1p2 is my root partition (yours is more likely to be something like /dev/sda2).
During resume I saw the image loading successfully, but in my case (just an example - YMMVAPD) then some more drivers (i2c_designware) threw some errors and I got a complete system freeze on resume. Hibernation works if I unload those modules in addition to brcmfmac, but the system quickly becomes unusable without those modules. I therefore made a sort of script to unload the buggy modules and immediately reinsert them on resume:
When I want to hibernate, I run sudo bash script. This works great.
TL;DR
Use systemd, set a boot parameter for resume from swap, identify buggy drivers and unload them before initiating hibernation. If the system can't work for long without those modules or you need to unload several, it may be easier to use a simple script to initiate hibernation.
It opens nano with an empty file. Copy the lines below and paste them into the nano window.
[Re-enable hibernate by default in upower]
Identity=unix-user:*
Action=org.freedesktop.upower.hibernate
ResultActive=yes
[Re-enable hibernate by default in logind]
Identity=unix-user:*
Action=org.freedesktop.login1.hibernate;org.freedesktop.login1.handle-hibernate-key;org.freedesktop.login1;org.freedesktop.login1.hibernate-multiple-sessions;org.freedesktop.login1.hibernate-ignore-inhibit
ResultActive=yes
Then save the changes and close nano and reboot the system to make Hibernate available appear on "Power options".
I think, how to enable hibernate for 16.04 answer is known to all as described in the Ubuntu Wiki (See below if you need the steps). But The things that need checking isn't thorough I think. At least, that's what I found.
Things to check
From my own tests, I've at least found one extra check that you should perform. I haven't found about it anywhere in the Internet.
Here are some checkings -
Check that you're not using any btrfs partitions. Yes. From my test, I found that if you have btrfs partitions, hibernate will not work. Removing or changing the partition type to ext4 didn't help me. I needed to remove the btrfs-tools package.
sudo apt-get purge btrfs-tools
You might want to check other new partition types which are not well tested. Without removing package, blacklisting the driver might also work, but I haven't tested that.
Also you need to check that you have a swap partition large enough to hold the content of RAM. If your RAM is 4 GB, swap should be at least 4 GB large ( You should allocate few more MB to be safe).
Steps to enable hibernate
It involves these steps
Create a file as root in /etc/polkit-1/localauthority/50-local.d/enable-hibernate.pkla
[Re-enable hibernate by default in upower]
Identity=unix-user:*
Action=org.freedesktop.upower.hibernate
ResultActive=yes
[Re-enable hibernate by default in logind]
Identity=unix-user:*
Action=org.freedesktop.login1.hibernate;org.freedesktop.login1.handle-hibernate-key;org.freedesktop.login1;org.freedesktop.login1.hibernate-multiple-sessions;org.freedesktop.login1.hibernate-ignore-inhibit
ResultActive=yes
Save the file by pressing Ctrl-O. Exit with Ctrl-X
(I asked a similar question asking for a focus on systemd-based replies, sharing my solution here for people following this question)
This solution comes from Fedora topics (they made the switch to systemd a while ago so there's more material there).
In my case (fresh 16.04.1 install on a machine that always supported hibernation), calling the obsolete sudo pm-hibernate did not seem to do anything, and the up to date systemd approach, systemctl hibernate, would return:
Failed to hibernate system via logind: Sleep verb not supported
It turns out that secure boot was the culprit: installing 16.04 you are asked what you want to do with it (which is a new thing as far as I can recall) and I kept it ON without giving it much thought.
On my machine with secure boot ON, cat /sys/power/disk answered:
[disabled]
After reboot and disabling secure boot in the BIOS settings (these are machine-specific, but usually pretty straightforward) I tried a cat /sys/power/disk and got:
[platform] shutdown reboot suspend
which looks better. And indeed calling systemctl hibernate results in a successful hibernate/thaw sequence.
Moreover, after that I could see hibernation available as an option in various places of the graphical interface, without the need of any polkit hack. So it seems that systemd was actually guessing from /sys/power/disk that the system was not able to hibernate.
Trying to put the system into hibernate (deep sleep where RAM is written to disk), generated the following error
$ sudo systemctl hibernate
Failed to hibernate system via logind: Sleep verb not supported
The following steps resolve the issue (Tested on Thinkpad X1 Carbon 7th Gen, Ubuntu 19.10). Most of them are borrowed from here.
Turn off Secure Boot in BIOS.
Set "Sleep State" to Linux in BIOS. This options was originally named "Modern Standby" in my BIOS and I had to turn if off, but after a BIOS name the name was changed to "Sleep State".
Create a swap file equal or bigger than RAM. Several steps are involved here which are as follows.
a. Turn off swap.
$ sudo swapoff -a
b. Create a file bigger or equal to the RAM. Mine is 16GB, so:
$ sudo dd if=/dev/zero of=/swapfile bs=1G count=16
16+0 records in
16+0 records out
17179869184 bytes (17 GB, 16 GiB) copied, 19.3685 s, 887 MB/s
c. Set the right permissions for the file:
$ sudo chmod 600 /swapfile
d. Make the file as swap:
$ sudo mkswap /swapfile
Setting up swapspace version 1, size = 16 GiB (17179865088 bytes)
no label, UUID=3b2e6f0c-ce12-4a84-9044-d99bfba059ea
e. Turn on swap and check if it is set properly:
$ sudo swapon /swapfile
$ cat /proc/swaps
Filename Type Size Used Priority
/swapfile file 16777212 0 -2
f. In order to make the swap be loaded after reboot, we have to add it to /etc/fstab. Thus run the following command to open the file:
$ sudo gedit /etc/fstab
And update it by adding the last line like below. Note that I have also commented my original swap as I don't need it.
/dev/mapper/vgubuntu-root / ext4 errors=remount-ro 0 1
# /boot was on /dev/nvme0n1p2 during installation
UUID=d265e7c4-1a4f-49c4-af29-fea2543490d7 /boot ext4 defaults 0 2
# /boot/efi was on /dev/nvme0n1p1 during installation
UUID=0004-FB5F /boot/efi vfat umask=0077 0 1
#/dev/mapper/vgubuntu-swap_1 none swap sw 0 0
/swapfile none swap sw 0 0
g. Do a reboot and run this command to see if the swap shows up:
cat /proc/swaps
Filename Type Size Used Priority
/swapfile file 16777212 0 -2
Now, it's time to update the grub.
a. Run this command to open grub:
$ sudoedit /etc/default/grub
b. Find where root is mounted by running the following command.
$ mount | grep " / "
/dev/mapper/vgubuntu-root on / type ext4 (rw,relatime,errors=remount-ro)
c. So mind is mounted on /dev/mapper/vgubuntu-root. Find the UUID of this location by running:
The UUID in this case is 2331fe68-3e7a-4937-9cfa-74fc7a4b79f6. Keep this UUID.
d. Next, we need to find the offset of the swap file. Run this command:
$ sudo filefrag -v /swapfile
Filesystem type is: ef53
File size of /swapfile is 17179869184 (4194304 blocks of 4096 bytes)
ext: logical_offset: physical_offset: length: expected: flags:
0: 0.. 32767: 835584.. 868351: 32768:
1: 32768.. 49151: 868352.. 884735: 16384:
2: 49152.. 81919: 886784.. 919551: 32768:
...
We look for the pysical_offset of the first block. In the above case, it will is 835584. Keep this number too.
e. We need to update the grub now. Run the following command:
$ sudoedit /etc/default/grub
Update with the following content. We update GRUB_CMDLINE_LINUX_DEFAULT and add GRUB_RECORDFAIL_TIMEOUT=0.
# If you change this file, run 'update-grub' afterwards to update
# /boot/grub/grub.cfg.
# For full documentation of the options in this file, see:
# info -f grub -n 'Simple configuration'
GRUB_DEFAULT=0
GRUB_TIMEOUT_STYLE=hidden
GRUB_TIMEOUT=0
GRUB_DISTRIBUTOR=`lsb_release -i -s 2> /dev/null || echo Debian`
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash resume=UUID=2331fe68-3e7a-4937-9cfa-74fc7a4b79f6 resume_offset=835584"
GRUB_CMDLINE_LINUX=""
# Avoiding grub to show up in boot when resuming from hibernation
GRUB_RECORDFAIL_TIMEOUT=0
f. Once the grub file is updated, run this command:
$ sudo update-grub
That should be it. Now you can put the system into hibernation by running
For me, it works to install hibernate package, reboot and then run sudo hibernate-disk. I am sure it is possible to add it to menu, but is not worth the time for me.
This instruction worked for my Ubuntu 18.04 installation.
sudo apt install hibernate It will install hibernate and other dependencies which are needed to hibernate
grep swap /etc/fstab (fing UUID)
sudoedit /etc/default/grub
At the line GRUB_CMDLINE_LINUX_DEFAULT="quiet splash" add UUID of swap. The line looks like this GRUB_CMDLINE_LINUX_DEFAULT="quiet splash resume=UUID of swap"
sudo update-grub
Restart, and after restart sudo systemctl hibernate. If everything works ok add menu entry's.
sudo gedit /etc/polkit-1/localauthority/50-local.d/com.ubuntu.enable-hibernate.pkla
now paste this:
[Re-enable hibernate by default in upower]
Identity=unix-user:*
Action=org.freedesktop.upower.hibernate
ResultActive=yes
[Re-enable hibernate by default in logind]
Identity=unix-user:*
Action=org.freedesktop.login1.hibernate;org.freedesktop.login1.handle-hibernate-key;org.freedesktop.login1;org.freedesktop.login1.hibernate-multiple-sessions;org.freedesktop.login1.hibernate-ignore-inhibit
ResultActive=yes
Expanding on my own comment to kelvinelove's answer, the file he suggests editing did not exist on my system (fresh Ubuntu 16.04). Instead, I did this:
Look for these sections (they are right by each other):
[Disable hibernate by default in upower] Identity=unix-user:*
Action=org.freedesktop.upower.hibernate ResultActive=no
[Disable hibernate by default in logind] Identity=unix-user:*
Action=org.freedesktop.login1.hibernate;org.freedesktop.login1.handle-hibernate-key;
ResultActive=no
Change ResultActive=no to ResultActive=yes for both of them.
Press Ctrl + O to save the file.
Reboot your computer
The Hibernate option is now available in your power menus.
EDIT: Gunnar pointed out that this file gets overwritten if a certain package gets updated, so depending on your intentions it is most likely not the best solution.
First, I do recommend that you test if your machine supports hibernation, because the reason why hibernation is disabled by default is because it sometimes has unpleasant results on some machines. Test your machine by opening the terminal (Ctrl+Alt+T) and then typing sudo pm-hibernate
Your machine should hibernate. Wake your machine up after hibernation and observe if it misbehaves or if it acts normally.
If you experience any abnormality after the hibernation, then I advise you don't continue with the following procedure. However, if it works just fine, continue to activate hibernation by doing this:
Hibernation using
systemctl
and getting it working in tough casesFor me,
pm-hibernate
always fails. After some tweaks, I was able to hibernate using the interface of systemd (init system in 16.04 and above). I also managed to get it working on 17.04 with a swap file. This case study may be useful for others with problems.First try:
If that fails, begin troubleshooting: in the hibernate state (HTD or ACPI S4) the machine state is written to disk so that no power is needed to preserve it. The state is written either to a swap partition or to a swap file. Note: if using Btrfs DO NOT attempt to use a swap file as this may cause filesystem corruption
Your swap partition or swap file may need to be the same size as RAM to allow hibernation, but there is a good chance you will be able to hibernate if it is at least 2/5 the size of RAM, according to the Arch wiki page, so try other steps first before increasing swap size.
If your problem is that you get a clean boot instead of the expected resume, at a minimum you most likely need to set a boot parameter to find the disk image
Find your swap partition:
for me this returns (partial output)
where
/dev/mmcblk0p3
is the partition to specifyAdd a boot parameter:
To the line starting
GRUB_CMDLINE_LINUX_DEFAULT
addresume=/dev/YourSwapPartition
to the section in quotes (replace with the the partition you identified earlier). Using my example:Any time you change this file, you must run
sudo update-grub
or the changes will have no effect.Now you need to reboot. Then you can try to hibernate, by issuing the command:
To resume, press the power button and the system will boot.
If you still have problems, start debugging.
I include my case below as an example, but detailed information on debugging S states can be found in this blog and also this one.
Set some more boot parameters to capture more information. Remove
quiet
andsplash
and addinitcall_debug
andno_console_suspend
which will cause init system calls to be printed to the console so you can watch what is going wrong. I set this:Which helped me see what was going wrong on resume from hibernation. You can also try using
dmesg
.In my case, after resume I lost WiFi, and the kernel clearly was upset as most commands (for example reading anything from
/sys
, reloading modules or anysystemctl
command) would not work - the process would appear to start and just hang (all this would be returned to normal after reboot of course). Watching the system very slowly shut down and reading all the debug messages, I noticed that there were a lot of problems with "brcm", so I guessed my Broadcom wireless driver module was to blame. Sure enough I adjusted my hibernation procedure to unload the module first:on resume I reinsert the module
And everything worked perfectly. I also have to blacklist the
btsdio
module which seems to be incompatible withbrcmfmac
Update: Hibernation using a swap file on 17.04.
Once again with help from the Arch wiki page and some additional tinkering, I managed to get hibernation to work on 17.04 with a swap file. This required an additional boot parameter,
resume_offset=n
where n is the first number underphysical_offset
in the output ofsudo filefrag -v /swapfile
:Therefore, the additional boot parameter in my case is
resume_offset=34816
. You still need to set a boot parameter for the partition to resume from. This will be the root partition (or whatever partition your swap file is located on) My parameters are now:Where
/dev/mmcblk1p2
is my root partition (yours is more likely to be something like/dev/sda2
).During resume I saw the image loading successfully, but in my case (just an example - YMMVAPD) then some more drivers (
i2c_designware
) threw some errors and I got a complete system freeze on resume. Hibernation works if I unload those modules in addition tobrcmfmac
, but the system quickly becomes unusable without those modules. I therefore made a sort of script to unload the buggy modules and immediately reinsert them on resume:When I want to hibernate, I run
sudo bash script
. This works great.TL;DR
Use systemd, set a boot parameter for resume from swap, identify buggy drivers and unload them before initiating hibernation. If the system can't work for long without those modules or you need to unload several, it may be easier to use a simple script to initiate hibernation.
You can use
to check if hibernate works on your system (this will hibernate your computer).
If it does not work , check if your swap size is at least as large as your RAM.
To add the option to the settings menu, you can create a configuration file. Open a terminal window and run this command:
It opens nano with an empty file. Copy the lines below and paste them into the nano window.
Then save the changes and close nano and reboot the system to make Hibernate available appear on "Power options".
Reference: How do I hibernate my computer? in the official documentation for Ubuntu 16.04.
Hope it works. This worked for me after trying all other options.
I think, how to enable hibernate for 16.04 answer is known to all as described in the Ubuntu Wiki (See below if you need the steps). But The things that need checking isn't thorough I think. At least, that's what I found.
Things to check
From my own tests, I've at least found one extra check that you should perform. I haven't found about it anywhere in the Internet.
Here are some checkings -
Check that you're not using any btrfs partitions. Yes. From my test, I found that if you have btrfs partitions, hibernate will not work. Removing or changing the partition type to
ext4
didn't help me. I needed to remove thebtrfs-tools
package.You might want to check other new partition types which are not well tested. Without removing package, blacklisting the driver might also work, but I haven't tested that.
Also you need to check that you have a swap partition large enough to hold the content of RAM. If your RAM is 4 GB, swap should be at least 4 GB large ( You should allocate few more MB to be safe).
Steps to enable hibernate
It involves these steps
Create a file as root in
/etc/polkit-1/localauthority/50-local.d/enable-hibernate.pkla
Put these contents on that file
Save the file by pressing Ctrl-O. Exit with Ctrl-X
Restart the
polkitd
daemonIt should enable hibernate.
Secure Boot
(I asked a similar question asking for a focus on systemd-based replies, sharing my solution here for people following this question)
This solution comes from Fedora topics (they made the switch to systemd a while ago so there's more material there).
In my case (fresh 16.04.1 install on a machine that always supported hibernation), calling the obsolete
sudo pm-hibernate
did not seem to do anything, and the up to date systemd approach,systemctl hibernate
, would return:It turns out that secure boot was the culprit: installing 16.04 you are asked what you want to do with it (which is a new thing as far as I can recall) and I kept it ON without giving it much thought.
On my machine with secure boot ON,
cat /sys/power/disk
answered:After reboot and disabling secure boot in the BIOS settings (these are machine-specific, but usually pretty straightforward) I tried a
cat /sys/power/disk
and got:which looks better. And indeed calling
systemctl hibernate
results in a successful hibernate/thaw sequence.Moreover, after that I could see hibernation available as an option in various places of the graphical interface, without the need of any
polkit
hack. So it seems thatsystemd
was actually guessing from/sys/power/disk
that the system was not able to hibernate.Trying to put the system into hibernate (deep sleep where RAM is written to disk), generated the following error
The following steps resolve the issue (Tested on Thinkpad X1 Carbon 7th Gen, Ubuntu 19.10). Most of them are borrowed from here.
Create a swap file equal or bigger than RAM. Several steps are involved here which are as follows.
a. Turn off swap.
b. Create a file bigger or equal to the RAM. Mine is 16GB, so:
c. Set the right permissions for the file:
d. Make the file as swap:
e. Turn on swap and check if it is set properly:
f. In order to make the swap be loaded after reboot, we have to add it to
/etc/fstab
. Thus run the following command to open the file:And update it by adding the last line like below. Note that I have also commented my original swap as I don't need it.
g. Do a reboot and run this command to see if the swap shows up:
Now, it's time to update the grub. a. Run this command to open grub:
b. Find where root is mounted by running the following command.
c. So mind is mounted on
/dev/mapper/vgubuntu-root
. Find the UUID of this location by running:The UUID in this case is
2331fe68-3e7a-4937-9cfa-74fc7a4b79f6
. Keep this UUID. d. Next, we need to find the offset of the swap file. Run this command:We look for the pysical_offset of the first block. In the above case, it will is
835584
. Keep this number too. e. We need to update the grub now. Run the following command:Update with the following content. We update
GRUB_CMDLINE_LINUX_DEFAULT
and addGRUB_RECORDFAIL_TIMEOUT=0
.f. Once the grub file is updated, run this command:
That should be it. Now you can put the system into hibernation by running
For me, it works to install
hibernate
package, reboot and then runsudo hibernate-disk
. I am sure it is possible to add it to menu, but is not worth the time for me.This instruction worked for my Ubuntu 18.04 installation.
sudo apt install hibernate
It will install hibernate and other dependencies which are needed to hibernategrep swap /etc/fstab
(fing UUID)sudoedit /etc/default/grub
At the line GRUB_CMDLINE_LINUX_DEFAULT="quiet splash" add UUID of swap. The line looks like this GRUB_CMDLINE_LINUX_DEFAULT="quiet splash resume=UUID of swap"sudo update-grub
sudo systemctl hibernate
. If everything works ok add menu entry's.sudo gedit /etc/polkit-1/localauthority/50-local.d/com.ubuntu.enable-hibernate.pkla
now paste this:copied from https://askubuntu.com/a/819891/712203
Expanding on my own comment to kelvinelove's answer, the file he suggests editing did not exist on my system (fresh Ubuntu 16.04). Instead, I did this:
sudo nano /var/lib/polkit-1/localauthority/10-vendor.d/com.ubuntu.desktop.pkla
Look for these sections (they are right by each other):
Change ResultActive=no to ResultActive=yes for both of them.
EDIT: Gunnar pointed out that this file gets overwritten if a certain package gets updated, so depending on your intentions it is most likely not the best solution.
Source: http://www.zedt.eu/tech/linux/enable-hibernation-xubuntu-16-04/
First, I do recommend that you test if your machine supports hibernation, because the reason why hibernation is disabled by default is because it sometimes has unpleasant results on some machines. Test your machine by opening the terminal (Ctrl+Alt+T) and then typing
sudo pm-hibernate
Your machine should hibernate. Wake your machine up after hibernation and observe if it misbehaves or if it acts normally. If you experience any abnormality after the hibernation, then I advise you don't continue with the following procedure. However, if it works just fine, continue to activate hibernation by doing this:
Edit the opened file and add this lines:
After this, restart your machine, and after logging in, you should see a hibernation option added on the power menu, on the top right settings corner.
There are some very good resources here to help you sort out some of the more common hibernate issues under Ubuntu.
In my case, running Ubuntu 16.10 on a Lenovo u300s, in order for hibernate to work correctly I had to do the following:
Edit
/etc/default/grub
to include the following line:The RESUME refers to your specific swap file UUID. In particular, on my machine setting
pci=nomsi
was the key.Best of luck!