Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I would like to execute a command such as

 notify-send 'a'

if my Linux machine has been idle for 5 minutes.

By idle, I mean the same thing a screen saver that gets activated would use to define "idle".

share|improve this question
OK, what have you tried? What did google say? Have you attempted to find out how the screensaver detects this? Please take the time to search before posting questions here and read through How to ask a good question. – terdon Aug 29 '13 at 18:06
I only found a program xautolock but there are no examples – user249704 Aug 29 '13 at 18:14

I use a program called xprintidle to find out the X idle time, which I'm strongly guessing uses the same data source as screensavers. xprintidle doesn't really seem to have an upstream anymore, but the Debian package is alive and well.

It is a very simple application: it returns the amount of milliseconds since last X interaction:

$ sleep 1 && xprintidle
$ sleep 5 && xprintidle
$ sleep 10 && xprintidle

(note: due to the underlying system, it will consistently give a value in ms slightly lower than the "actual" idle time).

You can use this to create a script that runs a certain sequence after five minutes of idle time via e.g.:


# Wanted trigger timeout in milliseconds.

# Sequence to execute when timeout triggers.
trigger_cmd() {
    echo "Triggered action $(date)"


# ceil() instead of floor()
while sleep $(((sleep_time+999)/1000)); do
    if [ $idle -ge $IDLE_TIME ]; then
        if ! $triggered; then
        # Give 100 ms buffer to avoid frantic loops shortly before triggers.

The 100 ms offset is because of the earlier noted quirk that xprintidle will always return a time slightly lower than the "actual" idle time when executed like this. It will work without this offset, and will then be more accurate to a tenth of a second, but it will trigger the xprintidle check frantically during the last milliseconds before an interval end. Not a performance hog in any way, but I would find that inelegant.

I have used a similar approach in a Perl script (an irssi plugin) for quite some time, but the above was just written and has not really been tested except for a few trial runs during writing.

Try it by running it in a terminal within X. I recommend setting the timeout to e.g. 5000 ms for testing, and adding set -x directly below #!/bin/sh to get informative output to see how it works.

share|improve this answer

Here's a C application that I found which you can compile.

$ more xidle.c 
#include <stdio.h>
#include <X11/Xlib.h>
#include <X11/extensions/scrnsaver.h>

/* Report amount of X server idle time. */
/* Build with- */
/* cc xidle.c -o xidle -lX11 -lXext -lXss */

int main(int argc, char *argv[])
    Display *display;
    int event_base, error_base;
    XScreenSaverInfo info;
    float seconds;

    display = XOpenDisplay("");

    if (XScreenSaverQueryExtension(display, &event_base, &error_base)) {
    XScreenSaverQueryInfo(display, DefaultRootWindow(display), &info);

    seconds = (float)info.idle/1000.0f;
    else {
    fprintf(stderr,"Error: XScreenSaver Extension not present\n");

It needs a couple libraries to build. On my Fedora 19 system I needed the following libraries:

$ rpm -qf /lib64/ /lib64/ /lib64/

Once these were installed I compiled the above like so:

$ gcc xidle.c -o xidle -lX11 -lXext -lXss

You can see that it's able to report the number of seconds that X is detecting as idle time by running it like so:

$ while [ 1 ]; do ./xidle ; sleep 2;done
0.073000   <--- moved the mouse here which resets it

Using this executable you could put together a script that can do something like this, monitoring the idle time reported by xidle.

$ while [ 1 ]; do idle=$(./xidle); 
    [ $( echo "$idle > 5" | bc ) -eq 0 ] && echo "still < 5" || echo "now > 5"; 
    sleep 2;
still < 5
still < 5
still < 5
now > 5
now > 5
still < 5
still < 5
still < 5

The above shows still < 5 until 5 seconds of idle time has elapsed, at which point it starts saying now > 5, which means that 5+ seconds has passed.

NOTE: You could incorporate your notify-send 'a' into the above example.


share|improve this answer

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.