BTRFS Swap "Not enough swap space for hibernation"

systemctl hibernate says Not enough swap space, but free -h indicates that “free” swap is greater than “total” mem.

$ systemctl hibernate
Call to Hibernate failed: Not enough swap space for hibernation

$ free -h
               total        used        free      shared  buff/cache   available
Mem:            15Gi       6.8Gi       199Mi       2.5Gi       8.4Gi       5.8Gi
Swap:           23Gi       9.0Mi        23Gi

If it matters (which I don’t think it should), my swap partition is a btrfs subvolume on luks encrypted disk.

$ swapon
NAME           TYPE SIZE   USED PRIO
/swap/swapfile file  24G 139.2M   -2

$ mount -v | grep swap
/dev/mapper/crypted on /swap type btrfs (rw,relatime,compress=zstd:3,ssd,noacl,space_cache=v2,subvolid=260,subvol=/swap)

$ cat /etc/fstab | grep -i swap
# To make changes, edit the fileSystems and swapDevices NixOS options
/dev/mapper/crypted /swap btrfs subvol=swap 0 0
# Swap devices.
/swap/swapfile none swap defaults

$ sudo btrfs sub list / | grep swap
ID 260 gen 6590 top level 5 path swap

My disk configuration here. It uses disko, so I found it easier to just nix repl and evaluate whatever attributes you need to answer the question.

$ nix repl '.#nixosConfigurations.laptop'
Welcome to Nix 2.19.2. Type :? for help.

Loading installable 'git+file:///home/sam/box/homelab#nixosConfigurations.laptop'...
Added 9 variables.
nix-repl> config.boot.kernelParams
[ "acpi_osi=\"!Windows 2020\"" "nvme.noacpi=1" "loglevel=4" ]
(some NixOS systems would have "nohibernate" in here; not me.)

nix-repl> config.fileSystems
{ "/" = { ... }; "/boot" = { ... }; "/home" = { ... }; "/nix" = { ... }; "/persist" = { ... }; "/swap" = { ... }; "/var/log" = { ... }; }

nix-repl> config.fileSystems."/swap"
{ autoFormat = false; autoResize = false; depends = [ ... ]; device = "/dev/mapper/crypted"; encrypted = { ... }; formatOptions = null; fsType = "btrfs"; label = null; mountPoint = "/swap"; neededForBoot = false; noCheck = false; options = [ ... ]; stratis = { ... }; }

nix-repl> config.swapDevices               
[ { ... } ]

nix-repl> (builtins.head config.swapDevices).device
"/swap/swapfile"
1 Like

In journalctl or dmesg you may have the reason why it doesn’t want to hibernate.

For instance, if the swap file is on a BTRFS volume spread across more than 1 disk, it will refuse.

Neither journalctl nor dmesg contain the word “swap” or “hibernate” case insensitive. Not sure what’s going on here.

same configuration here and same problem
also nothing shows in my journalctl or dmesg

I had this error myself (couple releases ago). In my particular issue it was a systemd bug (not sure if its still a bug or the same issue your hitting). In my particular case the workaround (knowing that the swap size is of sufficient size):

# In your NixOS configuration
systemd.services.systemd-logind.environment = {
   SYSTEMD_BYPASS_HIBERNATION_MEMORY_CHECK = "1";
};

@Solene
good news I found some new context using @simplejack-src hacks
so at least we know where is the problem
and make this bug report
https://github.com/NixOS/nix/issues/9660

1 Like