While the commonly suggested method of masking systemd targets works superficially:
sudo systemctl mask sleep.target suspend.target hibernate.target hybrid-sleep.target
It creates significant overhead as systemd-logind continuously attempts and fails to suspend, resulting in:
- 100% CPU usage by systemd-logind
- Flooded system logs with permission denied errors
- Poor resource utilization on your server
The correct approach is to modify the Login Manager configuration:
sudo nano /etc/systemd/logind.conf
Uncomment and modify these lines:
HandleLidSwitch=ignore
HandleLidSwitchExternalPower=ignore
IdleAction=ignore
For complete control, combine with these configurations:
# Disable automatic suspend
gsettings set org.gnome.settings-daemon.plugins.power sleep-inactive-ac-type 'nothing'
gsettings set org.gnome.settings-daemon.plugins.power sleep-inactive-battery-type 'nothing'
# Disable screen blanking (even without X)
sudo systemctl mask console-getty.service
sudo systemctl stop console-getty.service
After making changes, restart the login service and verify:
sudo systemctl restart systemd-logind
systemd-detect-virt # Check if running as VM (may affect behavior)
journalctl -u systemd-logind -b | grep -i suspend # Monitor for errors
For physical servers where you want to completely disable ACPI lid events:
sudo nano /etc/default/acpi-support
# Add or modify:
ACPI_LID=N
Then rebuild initramfs:
sudo update-initramfs -u
Create a test script to monitor suspension attempts:
#!/bin/bash
while true; do
if grep -q "suspend" /proc/acpi/wakeup; then
echo "Suspend still enabled on: $(grep "suspend" /proc/acpi/wakeup)"
sleep 5
else
echo "Suspend properly disabled"
break
fi
done
When running Ubuntu 20.04 as a headless server, the default suspend behavior becomes problematic. While systemctl mask
commands technically prevent suspension, they create a vicious cycle:
# This "solution" causes CPU spikes
sudo systemctl mask sleep.target suspend.target hibernate.target hybrid-sleep.target
You'll see constant log spam and 100% CPU usage from systemd-logind as it repeatedly attempts (and fails) to suspend:
journalctl -f
# Output:
systemd-logind[514]: Suspending...
systemd-logind[514]: Unit suspend.target is masked, refusing operation.
systemd-logind[514]: Failed to execute suspend operation: Permission denied
Instead of masking targets, we need to configure logind to ignore lid events entirely:
sudo nano /etc/systemd/logind.conf
Modify or add these key parameters:
HandleLidSwitch=ignore
HandleLidSwitchExternalPower=ignore
HandleLidSwitchDocked=ignore
IdleAction=ignore
For complete prevention of unwanted power state changes:
sudo systemctl unmask sleep.target suspend.target hibernate.target hybrid-sleep.target
sudo systemctl stop systemd-suspend.service
sudo systemctl mask systemd-suspend.service
Then create a udev rule to handle lid events:
sudo nano /etc/udev/rules.d/80-disable-lid-suspend.rules
Add this content:
# Disable lid switch handling
SUBSYSTEM=="input", ACTION=="change", ENV{LID_SWITCH}=="1", RUN+="/bin/true"
After making these changes:
sudo systemctl restart systemd-logind.service
sudo udevadm control --reload
Test by closing the lid and monitoring:
journalctl -f -u systemd-logind
uptime
You should see no suspension attempts and normal CPU usage.
For systems where sleep states should never be available:
sudo systemctl disable suspend.target
sudo systemctl disable hibernate.target
sudo systemctl disable hybrid-sleep.target
Then add kernel parameters:
sudo nano /etc/default/grub
# Append to GRUB_CMDLINE_LINUX_DEFAULT:
mem_sleep_default=deep noplymouth nosplash
Update GRUB:
sudo update-grub