]> git.sesse.net Git - vlc/blob - modules/misc/screensaver.c
screensaver: convert to inhibit plugin
[vlc] / modules / misc / screensaver.c
1 /*****************************************************************************
2  * screensaver.c : disable screen savers when VLC is playing
3  *****************************************************************************
4  * Copyright (C) 2006-2009 the VideoLAN team
5  * $Id$
6  *
7  * Authors: Sam Hocevar <sam@zoy.org>
8  *          Benjamin Pracht <bigben AT videolan DOT org>
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License as published by
12  * the Free Software Foundation; either version 2 of the License, or
13  * (at your option) any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU General Public License for more details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with this program; if not, write to the Free Software
22  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
23  *****************************************************************************/
24
25 /*****************************************************************************
26  * Preamble
27  *****************************************************************************/
28
29 #ifdef HAVE_CONFIG_H
30 # include "config.h"
31 #endif
32
33 #include <vlc_common.h>
34 #include <vlc_plugin.h>
35 #include <vlc_inhibit.h>
36
37 #include <sys/types.h>
38 #include <sys/wait.h>
39 #include <unistd.h>
40 #include <signal.h>
41
42 /*****************************************************************************
43  * Local prototypes
44  *****************************************************************************/
45 static int  Activate     ( vlc_object_t * );
46 static void  Deactivate   ( vlc_object_t * );
47
48 static void Timer( void * );
49 static void Inhibit( vlc_inhibit_t *, bool );
50
51 struct vlc_inhibit_sys
52 {
53     vlc_timer_t timer;
54 };
55
56
57 /*****************************************************************************
58  * Module descriptor
59  *****************************************************************************/
60 vlc_module_begin ()
61     set_description( N_("X Screensaver disabler") )
62     set_capability( "inhibit", 5 )
63     set_callbacks( Activate, Deactivate )
64 vlc_module_end ()
65
66 /*****************************************************************************
67  * Activate: initialize and create stuff
68  *****************************************************************************/
69 static int Activate( vlc_object_t *p_this )
70 {
71     vlc_inhibit_t *p_ih = (vlc_inhibit_t*)p_this;
72     vlc_inhibit_sys_t *p_sys;
73
74     p_sys = p_ih->p_sys = malloc( sizeof( *p_sys ) );
75     if( !p_sys )
76         return VLC_ENOMEM;
77
78     if( vlc_timer_create( &p_sys->timer, Timer, p_ih ) )
79     {
80         free( p_sys );
81         return VLC_ENOMEM;
82     }
83     p_ih->inhibit = Inhibit;
84
85     return VLC_SUCCESS;
86 }
87
88 /*****************************************************************************
89  * Deactivate: uninitialize and cleanup
90  *****************************************************************************/
91 static void Deactivate( vlc_object_t *p_this )
92 {
93     vlc_inhibit_t *p_ih = (vlc_inhibit_t*)p_this;
94     vlc_inhibit_sys_t *p_sys = p_ih->p_sys;
95
96     vlc_timer_destroy( p_sys->timer );
97
98     free( p_sys );
99 }
100
101 static void Inhibit( vlc_inhibit_t *p_ih, bool suspend )
102 {
103     mtime_t d = suspend ? 30*CLOCK_FREQ : 0;
104     vlc_timer_schedule( p_ih->p_sys->timer, false, d, d );
105 }
106
107 /*****************************************************************************
108  * Execute: Spawns a process using execv()
109  *****************************************************************************/
110 static void Execute( vlc_object_t *p_this, const char *const *ppsz_args )
111 {
112     pid_t pid = fork();
113     switch( pid )
114     {
115         case 0:     /* we're the child */
116         {
117             sigset_t set;
118             sigemptyset (&set);
119             pthread_sigmask (SIG_SETMASK, &set, NULL);
120
121             /* We don't want output */
122             if( ( freopen( "/dev/null", "w", stdout ) != NULL )
123              && ( freopen( "/dev/null", "w", stderr ) != NULL ) )
124                 execv( ppsz_args[0] , (char *const *)ppsz_args );
125             /* If the file we want to execute doesn't exist we exit() */
126             exit( EXIT_FAILURE );
127         }
128         case -1:    /* we're the error */
129             msg_Dbg( p_this, "Couldn't fork() while launching %s",
130                      ppsz_args[0] );
131             break;
132         default:    /* we're the parent */
133             /* Wait for the child to exit.
134              * We will not deadlock because we ran "/bin/sh &" */
135             while( waitpid( pid, NULL, 0 ) != pid);
136             break;
137     }
138 }
139
140 /*****************************************************************************
141  * Run: main thread
142  *****************************************************************************
143  * This part of the module is in a separate thread so that we do not have
144  * too much system() overhead.
145  *****************************************************************************/
146 static void Timer( void *data )
147 {
148     vlc_inhibit_t *p_ih = data;
149
150     /* If there is a playing video output, disable xscreensaver */
151     /* http://www.jwz.org/xscreensaver/faq.html#dvd */
152     const char *const ppsz_xsargs[] = { "/bin/sh", "-c",
153         "xscreensaver-command -deactivate &", (char*)NULL };
154     Execute( VLC_OBJECT(p_ih), ppsz_xsargs );
155
156     const char *const ppsz_gsargs[] = { "/bin/sh", "-c",
157         "gnome-screensaver-command --poke &", (char*)NULL };
158     Execute( VLC_OBJECT(p_ih), ppsz_gsargs );
159 }