Using a switch to prevent system shutdown/reboot/suspend

3 Comments

What I tried to accomplish today was to prevent a system shutdown or reboot or suspend, if a specific process was still running in the background. This might sound pretty useless, but having shut my PC down once again this afternoon while the backup process was still active in the background, I decided to resolve this issue for good. But things are not that easy as they might seem… After many hours of digging into the operating system’s initscripts, upstart events and the methods used by GNOME to perform a shutdown/reboot/suspend, I am still away from a decent solution that will, not only work when directly invoking the relevant commands from the console, but also when I perform the aforementioned actions from the GNOME shutdown applet. Here is what I’ve tried so far…

First of all, having failed with all the initscript or upstart event modifications I’ve tried, I decided to completely override the relevant commands, for instance /sbin/shutdown, by placing a wrapper script with the same name in /usr/local/sbin/. Here is such a wrapper script for the shutdown command, saved as /usr/local/sbin/shutdown:

#! /bin/sh
 
if [ -f /var/lock/noshutdown.lock ] ; then
  logger -t shutdowndog shutdown prevented
  exit 1
fi
 
/sbin/shutdown "$@"

Then, I created the file that would act as a switch:

touch /var/lock/noshutdown.lock

Then, I initiated the shutdown procedure from the command line:

shutdown -h +0

There was no shutdown! It had worked!

Syslog confirmed that the check had taken place:

Nov 25 19:19:04 galeon shutdowndog: shutdown prevented

I rushed to try to shut down the system from GNOME’s shutdonw panel (Menu System -> Shut Down...), but, after pressing the relevant button, the system went down normally…

It was obvious that GNOME had not used my override, but another mechanism to power-off the system instead. Since I use the GNOME menu to shutdown/reboot/suspend the system, I spent a couple of hours trying to find what was going on in GNOME and finally discovered the file /usr/bin/gnome-power-cmd.sh:

#!/bin/sh
# Copyright (C) 2007 Richard Hughes <richard@hughsie.com>
#
# Licensed under the GNU General Public License Version 2
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
 
#$1 = method name
execute_dbus_method ()
{
        dbus-send --session --dest=org.freedesktop.PowerManagement              \
                  --type=method_call --print-reply --reply-timeout=2000 \
                  /org/freedesktop/PowerManagement                      \
                  org.freedesktop.PowerManagement.$1
        if [ $? -eq 0 ]; then
                echo "Failed"
        fi
}
 
if [ "$1" = "suspend" ]; then
        echo "Suspending"
        execute_dbus_method "Suspend"
elif [ "$1" = "hibernate" ]; then
        echo "Hibernating"
        execute_dbus_method "Hibernate"
elif [ "$1" = "reboot" ]; then
        echo "Rebooting"
        execute_dbus_method "Reboot"
elif [ "$1" = "shutdown" ]; then
        echo "Shutting down"
        execute_dbus_method "Shutdown"
elif [ "$1" = "" ]; then
        echo "command required: suspend, shutdown, hibernate or reboot"
else
        echo "command '$1' not recognised, only suspend, shutdown, hibernate or reboot are valid"
        exit 1
fi

So, GNOME makes the appropriate calls for power-related events through D-bus. I initially thought that GNOME used /usr/bin/gnome-power-cmd.sh whenever the shutdown/reboot/suspend button was pressed, so I modified it so to check for my switch (/var/lock/noshutdown.lock) and then proceed accordingly. It did not work out…

I had already spent much time on this, so I decided to quit. But, it is crucial for me to make this thing work and I will probably investigate it a bit more and report back at some later time.

Using a switch to prevent system shutdown/reboot/suspend by George Notaras is licensed under a Creative Commons Attribution-NonCommercial-ShareAlike 4.0 International License.
Copyright © 2008 - Some Rights Reserved

George Notaras avatar

About George Notaras

George Notaras is the editor of the G-Loaded Journal, a technical blog about Free and Open-Source Software. George, among other things, is an enthusiast self-taught GNU/Linux system administrator. He has created this web site to share the IT knowledge and experience he has gained over the years with other people. George primarily uses CentOS and Fedora. He has also developed some open-source software projects in his spare time.

3 responses on “Using a switch to prevent system shutdown/reboot/suspend

  1. kyle Permalink →

    You could tweak the if statement like this which should do the job;

    if [ -f /var/lock/noshutdown.lock ] ; then
    logger -t shutdowndog shutdown prevented
    exit 1
    elif [ “$1” = “suspend” ]; then
    echo “Suspending”
    execute_dbus_method “Suspend”
    elif [ “$1” = “hibernate” ]; then
    echo “Hibernating”
    execute_dbus_method “Hibernate”
    elif [ “$1” = “reboot” ]; then
    echo “Rebooting”
    execute_dbus_method “Reboot”
    elif [ “$1” = “shutdown” ]; then
    echo “Shutting down”
    execute_dbus_method “Shutdown”
    elif [ “$1” = “” ]; then
    echo “command required: suspend, shutdown, hibernate or reboot”
    else
    echo “command ‘$1’ not recognised, only suspend, shutdown, hibernate or reboot are valid”
    exit 1
    fi

  2. George Notaras Post authorPermalink →

    This is exactly what I tried, but it did not work out. Anyway, I have written a decent solution that will work on every occasion. I just didn’t have enough time to post it. I will do so very soon.

    Thanks for your feedback.

  3. Shumkar Permalink →

    Met the same problem while launching few X and forgetting about it. Very interested in that decent solution you found. Could you post it?