2012-11-07

The Problem

Recently, Arch Linux (my distribution of choice) switch to the systemd system initialization and service manager, and the change broke one specific piece of functionality on a few of my systems. Namely, running a script when the power button is pressed, and not doing anything until my script has finished running.

On both of my systems affected by this, the script would play an audio file and then possible do something else.

After a few days/weeks of trying to write a systemd service file that would do what I wanted to do, and swearing up a storm of frustration, I finally found a solution.

What is Systemd?

Systemd is a daemon startup manager for Linux that starts and stops daemons in parallel. For each daemon on a system, there is a systemd .service file that describes which daemons depend upon which other daemons.

It is the relationship between daemons that, to me, is what makes systemd so powerful. Instead of starting one daemon after another over a period of time, systemd will use the .service files to determine which daemons can be started at the same time. In theory this should reduce startup time, but I haven't seen much improvement yet.

Similarly, systemd shuts down daemons in parallel. And it was this parallel shutdown that was causing me problems. I couldn't have a shutdown script make a network request because the network shutdown so fast, and if the audio subsystem shutdown before my file played, I would hear nothing.

My Solution

DON'T LET SYSTEMD HANDLE THE POWERBUTTON PRESS! LET ACPI HANDLE IT. Sorry for yelling, but I wish someone had yelled that at me a few weeks ago.

Here is what I did (as root):

  1. enabled the community repo for pacman
  2. install acpi and acpid: pacman -S acpi acpid
  3. skip step 3
  4. enable the acpid service: systemctl enable acpid.service
  5. start the acpid service: systemctl start acpid.service
  6. edit /etc/systemd/logind.conf and replace #HandlePowerKey=poweroff with HandlePowerKey=ignore

Goody gum drops; the system is now configured to let acpi handle the powerbutton press. Now I need to configure acpi to run my script.

To do this, I edited the file /etc/acpi/handler.sh which is the handler for acpi events. The line logger 'PowerButton pressed' was replaced with logger 'PowerButton pressed' && PATH_TO_MY_SHUTDOWN_SCRIPT In my case, PATH_TO_MY_SHUTDOWN_SCRIPT is /usr/local/sbin/myshutdown and the file looks like:

#!/bin/sh  
gst-launch-0.10 playbin uri=file:///storage/opt/shutdown.ogg volume=0.7   
shutdown -h now &  

Now, when I press the power button, my script runs and it plays my shutdown file and then initiates the systemd parallel shutdown. BOOYAH!

What a relief that was. Now I can focus on my next systemd quest: running a script after the network manager has connected to the network.

Comments
2014-07-24 Anders:
Thanks!

From https://wiki.archlinux.org/index.php/Power_management#Hooks_in_.2Fusr.2Flib.2Fsystemd.2Fsystem-sleep you should be able to run custom scripts by placing them in /usr/lib/systemd/system-sleep
(logind should give argument 1 as post or pre for post or pre suspend), but for some reason I have not been able to make this trick work.
Name:
not required
Email:
not required (will not be displayed)
Website:
not required (will link your name to your site)
Comment:
required
Please do not post HTML code or bbcode unless you want it to show up as code in your post. (or if you are a blog spammer, in which case, you probably aren't reading this anyway).
Prove you are human by solving a math problem! I'm sorry, but due to an increase of blog spam, I've had to implement a CAPTCHA.
Problem:
9 minus 7
Answer:
required
  • Tags:
subscribe
 
2016
2015
2014
2013
2012
2011
2010
December
November
October
September
August
July
June
May
April
March
February
January
2009
December
November
October
September
August
July
June
May
April
March
February
January
2008