summaryrefslogtreecommitdiff
authorsandman <sandman>2002-06-02 01:42:05 (UTC)
committer sandman <sandman>2002-06-02 01:42:05 (UTC)
commit2205558adae76dc40a5c0f2dd83226a4d1c67eae (patch) (unidiff)
treee7e96aa694bab035c2c75f3c1b6dbceea07d4270
parent385a3d8034003a412fa73840bf985582bf6b4547 (diff)
downloadopie-2205558adae76dc40a5c0f2dd83226a4d1c67eae.zip
opie-2205558adae76dc40a5c0f2dd83226a4d1c67eae.tar.gz
opie-2205558adae76dc40a5c0f2dd83226a4d1c67eae.tar.bz2
Reworked the whole system and introduced re-suspend. Effect is that the
iPAQ is re-suspended when woken up by the RTC (as opposed to the button) and on AC. Timeout is currently hardcoded to 120sec.
Diffstat (more/less context) (ignore whitespace changes)
-rw-r--r--core/opiealarm/opiealarm.c246
-rwxr-xr-xcore/opiealarm/opieatd29
-rwxr-xr-xroot/etc/init.d/opieatd2
3 files changed, 217 insertions, 60 deletions
diff --git a/core/opiealarm/opiealarm.c b/core/opiealarm/opiealarm.c
index 33d631d..3a06236 100644
--- a/core/opiealarm/opiealarm.c
+++ b/core/opiealarm/opiealarm.c
@@ -1,167 +1,309 @@
1/* opiealarm.c 1/* opiealarm.c
2* This program is for extracting the event time/date out 2* This program is for extracting the event time/date out
3* of /etc/resumeat and setting the RTC alarm to that time/date. 3* of /etc/resumeat and setting the RTC alarm to that time/date.
4* It is designed to run via a script just before the iPaq 4* It is designed to run via a script just before the iPaq
5* is suspended. 5* is suspended.
6* 6*
7* Roughly based on ipaqalarm from Benjamin Long 7* Roughly based on ipaqalarm from Benjamin Long
8* 8*
9* written by Robert Griebl <sandman@handhelds.org> 9* written by Robert Griebl <sandman@handhelds.org>
10*/ 10*/
11 11
12#include <stdio.h> 12#include <stdio.h>
13#include <linux/rtc.h> 13#include <linux/rtc.h>
14#include <sys/ioctl.h> 14#include <sys/ioctl.h>
15#include <sys/time.h> 15#include <sys/time.h>
16#include <sys/types.h> 16#include <sys/types.h>
17#include <fcntl.h> 17#include <fcntl.h>
18#include <unistd.h> 18#include <unistd.h>
19#include <errno.h> 19#include <errno.h>
20#include <time.h> 20#include <time.h>
21#include <stdlib.h> 21#include <stdlib.h>
22#include <syslog.h> 22#include <syslog.h>
23#include <signal.h> 23#include <signal.h>
24#include <errno.h>
25#include <string.h>
24 26
25 27
26 #define PIDFILE "/var/run/opiealarm.pid" 28 #define PIDFILE "/var/run/opiealarm.pid"
29 #define APMFILE "/proc/apm"
30
31FILE *log; // debug only
27 32
28FILE *log; 33int resume ( void );
34int suspend ( void );
35int main ( int argc, char **argv );
36int fork_with_pidfile ( void );
37int kill_with_pidfile ( void );
38void remove_pidfile ( void );
39void usage ( void );
40void sig_handler ( int sig );
41void error_msg_and_die ( int perr, const char *msg );
42int onac ( void );
43
44static int opiealarm_was_running;
29 45
30 46
31void log_msg ( const char *msg ) 47void log_msg ( const char *msg )
32{ 48{
33 if ( log ) { 49 if ( log ) {
34 fprintf ( log, msg ); 50 fprintf ( log, msg );
35 fflush ( log ); 51 fflush ( log );
36 } 52 }
37} 53}
38 54
39void error_msg_and_die ( int perr, const char *msg ) 55void error_msg_and_die ( int perr, const char *msg )
40{ 56{
41 if ( perr ) 57 if ( perr )
42 log_msg ( strerror ( errno )); 58 log_msg ( strerror ( errno ));
43 log_msg ( msg ); 59 log_msg ( msg );
44 60
45 unlink ( PIDFILE ); 61 while ( 1 ) // pretend we are waiting on RTC, so opiealarm -r can kill us
62 sleep ( 1 );
63}
64
65
66void sig_handler ( int sig )
67{
68 log_msg ( "GOT SIGNAL -> EXITING\n" );
69 fclose ( log );
70 remove_pidfile ( );
71 exit ( 0 );
72}
73
74void usage ( void )
75{
76 fprintf ( stderr, "Usage: opiealarm -r|-s\n" );
46 exit ( 1 ); 77 exit ( 1 );
47} 78}
48 79
80int fork_with_pidfile ( void )
81{
82 FILE *fp;
83 pid_t pid;
84
85 pid = fork ( );
86
87 if ( pid > 0 )
88 exit ( 0 );
89 else if ( pid < 0 ) {
90 perror ( "forking failed" );
91 return 0;
92 }
93
94 signal ( SIGTERM, sig_handler );
95 signal ( SIGINT, sig_handler );
96
97 // save pid
98 if (( fp = fopen ( PIDFILE, "w" ))) {
99 fprintf ( fp, "%d", getpid ( ));
100 fclose ( fp );
101
102 // detach
103 close ( 0 );
104 close ( 1 );
105 close ( 2 );
106
107 setpgid ( 0, 0 );
108
109 return 1;
110 }
111 else {
112 perror ( PIDFILE );
113 return 0;
114 }
115}
116
117int kill_with_pidfile ( void )
118{
119 FILE *fp;
120 pid_t pid;
121
122 if (( fp = fopen ( PIDFILE, "r" ))) {
123 if ( fscanf ( fp, "%d", &pid ) == 1 )
124 return ( kill ( pid, SIGTERM ) == 0 ) ? 1 : 0;
125 fclose ( fp );
126 }
127 return 0;
128}
129
130void remove_pidfile ( void )
131{
132 unlink ( PIDFILE );
133
134 signal ( SIGTERM, SIG_DFL );
135 signal ( SIGINT, SIG_DFL );
136}
137
138
139int main ( int argc, char **argv )
140{
141 int mode = 0;
142 int opt;
143
144 while (( opt = getopt ( argc, argv, "rs" )) != EOF ) {
145 switch ( opt ) {
146 case 's':
147 mode = 's';
148 break;
149 case 'r':
150 mode = 'r';
151 break;
152 default:
153 usage ( );
154 }
155 }
156
157 if ( geteuid ( ) != 0 ) {
158 fprintf ( stderr, "You need root priviledges to run opiealarm." );
159 return 2;
160 }
161
162 if ( !mode )
163 usage ( );
164
165 // kill running opiealarm
166 opiealarm_was_running = kill_with_pidfile ( );
167 remove_pidfile ( );
168
169 if ( mode == 'r' )
170 return resume ( );
171 else
172 return suspend ( );
49 173
174 return 0;
175 }
176
50 177
51void suspend_on_rtc ( ) 178int suspend ( void )
52{ 179{
53 FILE *fp; 180 FILE *fp;
54 char buf [64]; 181 char buf [64];
55 time_t t; 182 time_t t;
56 struct tm *tm; 183 struct tm *tm;
57 int fd; 184 int fd;
185
186
187 if ( !fork_with_pidfile ( ))
188 return 3;
189
190 log = fopen ( "/tmp/opiealarm.log", "w" );
191 log_msg ( "STARTING\n" );
58 192
59 193
194
60 if (!( fp = fopen ( "/etc/resumeat", "r" ))) 195 if (!( fp = fopen ( "/etc/resumeat", "r" )))
61 error_msg_and_die ( 1, "/etc/resumeat" ); 196 error_msg_and_die ( 1, "/etc/resumeat" );
62 197
63 if ( !fgets ( buf, sizeof( buf ) - 1, fp )) 198 if ( !fgets ( buf, sizeof( buf ) - 1, fp ))
64 error_msg_and_die ( 1, "/etc/resumeat" ); 199 error_msg_and_die ( 1, "/etc/resumeat" );
65 200
66 fclose ( fp ); 201 fclose ( fp );
67 202
68 t = atoi ( buf ); 203 t = atoi ( buf );
69 204
70 if ( t == 0 ) 205 if ( t == 0 )
71 error_msg_and_die ( 0, "/etc/resumeat contains an invalid time description" ); 206 error_msg_and_die ( 0, "/etc/resumeat contains an invalid time description" );
72 207
73 /* subtract 5 sec from event time... */ 208 /* subtract 5 sec from event time... */
74 t -= 5; 209 t -= 5;
75 210
76 if ( log ) 211 if ( log )
77 fprintf ( log, "Setting RTC alarm to %d\n", t ); 212 fprintf ( log, "Setting RTC alarm to %d\n", t );
78 213
79 tm = gmtime ( &t ); 214 tm = gmtime ( &t );
80 215
81 // Write alarm time to RTC 216 // Write alarm time to RTC
82 if (( fd = open ( "/dev/misc/rtc", O_RDWR ) < 0 ); 217 if (( fd = open ( "/dev/misc/rtc", O_RDWR )) < 0 )
83 error_msg_and_die ( 1, "/dev/misc/rtc" ); 218 error_msg_and_die ( 1, "/dev/misc/rtc" );
84 // set alarm time 219 // set alarm time
85 if ( ioctl ( fd, RTC_ALM_SET, tm ) < 0 ) 220 if ( ioctl ( fd, RTC_ALM_SET, tm ) < 0 )
86 error_msg_and_die ( 1, "ioctl RTC_ALM_SET" ); 221 error_msg_and_die ( 1, "ioctl RTC_ALM_SET" );
87 // enable alarm irq 222 // enable alarm irq
88 if ( ioctl ( fd, RTC_AIE_ON, 0 ) < 0 ) 223 if ( ioctl ( fd, RTC_AIE_ON, 0 ) < 0 )
89 error_msg_and_die ( 1, "ioctl RTC_AIE_ON" ); 224 error_msg_and_die ( 1, "ioctl RTC_AIE_ON" );
90 225
91 log_msg ( "SLEEPING\n" ); 226 log_msg ( "SLEEPING\n" );
92 227
93 // wait for alarm irq 228 // wait for alarm irq
94 if ( read ( fd, buf, sizeof( unsigned long )) < 0 ) 229 if ( read ( fd, buf, sizeof( unsigned long )) < 0 )
95 error_msg_and_die ( 1, "read rtc alarm" ); 230 error_msg_and_die ( 1, "read rtc alarm" );
96 231
97 log_msg ( "WAKEUP\n" ); 232 log_msg ( "WAKEUP\n" );
98 233
99 // disable alarm irq 234 // disable alarm irq
100 if ( ioctl ( fd, RTC_AIE_OFF, 0 ) < 0 ) 235 if ( ioctl ( fd, RTC_AIE_OFF, 0 ) < 0 )
101 error_msg_and_die ( 1, "ioctl RTC_AIE_OFF" ); 236 error_msg_and_die ( 1, "ioctl RTC_AIE_OFF" );
102 237
103 close ( fd ); 238 close ( fd );
104} 239
105 240 log_msg ( "EXITING\n" );
106 241
107void sig_handler ( int sig )
108{
109 log_msg ( "GOT SIGNAL -> EXITING\n" );
110 fclose ( log ); 242 fclose ( log );
111 unlink ( PIDFILE ); 243 remove_pidfile ( );
112 exit ( 0 ); 244
245 return 0;
113} 246}
114 247
115 248
116int main ( ) 249static int onac ( void )
117{ 250{
118 FILE *fp; 251 FILE *fp;
119 pid_t pid; 252 int on = 0;
120 253
121 if ( geteuid ( ) != 0 ) { 254 if (( fp = fopen ( APMFILE, "r" ))) {
122 fprintf ( stderr, "You need root priviledges to run opiealarm." ); 255 int ac = 0;
123 return 1;
124 }
125 256
126 pid = fork ( ); 257 if ( fscanf ( fp, "%*[^ ] %*d.%*d 0x%*x 0x%x 0x%*x 0x%*x %*d%% %*i %*c", &ac ) == 1 )
127 258 on = ( ac == 0x01 ) ? 1 : 0;
128 if ( pid > 0 ) 259
129 return 0; 260 fclose ( fp );
130 else if ( pid < 0 ) {
131 perror ( "Could not fork." );
132 return 2;
133 }
134
135 // save pid
136 if (!( fp = fopen ( PIDFILE, "w" ))) {
137 perror ( PIDFILE );
138 return 3;
139 } 261 }
140 262 return on;
141 fprintf ( fp, "%d", getpid ( )); 263}
142 fclose ( fp );
143 264
144 // detach 265int resume ( void )
145 close ( 0 ); 266{
146 close ( 1 ); 267 FILE *fp;
147 close ( 2 );
148 268
149 setpgid ( 0, 0 ); 269 // re-suspend when on AC (optional) when woken up via RTC
150 270
151 log = fopen ( "/tmp/opiealarm.log", "w" ); 271 if ( !opiealarm_was_running ) { // opiealarm -s got it's RTC signal -> wake up by RTC
152 log_msg ( "STARTING\n" ); 272 if ( onac ( )) {
153 273 time_t start, now;
154 signal ( SIGTERM, sig_handler ); 274 char *argv [4];
155 signal ( SIGINT, sig_handler ); 275
276 if ( !fork_with_pidfile ( ))
277 return 4;
156 278
157 extractevent ( ); 279 // sleep 120sec (not less!)
158 280 time ( &start );
159 signal ( SIGTERM, SIG_DFL ); 281 do {
160 signal ( SIGINT, SIG_DFL ); 282 sleep ( 1 );
283 time ( &now );
284 } while (( now - start ) < 120 );
161 285
162 log_msg ( "EXITING\n" ); 286 if ( onac ( )) { // still on ac
287 // system() without fork
288 argv[0] = "qcop";
289 argv[1] = "QPE/Desktop";
290 argv[2] = "suspend()";
291 argv[3] = 0;
163 292
164 fclose ( log ); 293 // hard coded for now ...but needed
165 unlink ( PIDFILE ); 294 setenv ( "LOGNAME", "root", 1 );
295 setenv ( "HOME", "/root", 1 );
296 setenv ( "LD_LIBRARY_PATH", "/opt/QtPalmtop/lib", 1 );
297 setenv ( "QTDIR", "/opt/QtPalmtop", 1 );
298
299 remove_pidfile ( );
300
301 execv ( "/opt/QtPalmtop/bin/qcop", argv );
302
303 perror ( "exec for qcop failed" );
304 return 5;
305 }
306 }
307 }
166 return 0; 308 return 0;
167} 309}
diff --git a/core/opiealarm/opieatd b/core/opiealarm/opieatd
index 3b9dc0e..fc2d421 100755
--- a/core/opiealarm/opieatd
+++ b/core/opiealarm/opieatd
@@ -1,22 +1,37 @@
1#!/bin/sh 1#!/bin/sh
2 2
3timefile=/etc/resumeat 3timefile=/etc/resumeat
4 4
5trap exit 0 SIGTERM SIGINT SIGQUIT
6
7echo $$ >/var/run/opieatd.pid
8
5mkdir -p /var/spool/at 9mkdir -p /var/spool/at
6[ -p /var/spool/at/trigger ] || mkfifo /var/spool/at/trigger 10[ -p /var/spool/at/trigger ] || mkfifo /var/spool/at/trigger
7 11
8while true; do 12while true; do
9 cat /var/spool/at/trigger | while read line; do 13 while read </var/spool/at/trigger dummy; do
10 FILE=`ls -1 /var/spool/at/[0-9]* | head -n1` 14 FILES=`ls /var/spool/at/[0-9]* 2>/dev/null`
11 echo "File = $FILE" 15
12 if [ -z "$FILE" ]; then 16 if [ -z "$FILES" ]; then
13 echo "clear resume at" 17 echo "clear resume at"
14 echo "" >$timefile 18 echo "" >$timefile
15 else 19 else
16 unixtime=`basename $FILE | cut -c1-10` 20 for i in "$FILES"; do
17 echo "Datestring = $unixtime" 21 echo "File = $i"
18 echo "$unixtime" >$timefile 22
23 unixtime=`basename $i | cut -c1-10`
24 pid=`basename $i | cut -c12-`
25
26 if [ -d /proc/$pid ]; then
27 echo "Datestring = $unixtime"
28 echo "$unixtime" >$timefile
29 else
30 rm -f $i
31 fi
32 done
19 fi 33 fi
20 done 34 done
21done 35done
22 36
37exit 0
diff --git a/root/etc/init.d/opieatd b/root/etc/init.d/opieatd
index 83f6035..765426c 100755
--- a/root/etc/init.d/opieatd
+++ b/root/etc/init.d/opieatd
@@ -1,15 +1,15 @@
1#!/bin/sh 1#!/bin/sh
2 2
3PATH=/usr/bin:/bin 3PATH=/usr/bin:/bin
4HOME=/root 4HOME=/root
5 5
6case "$1" in 6case "$1" in
7 start) 7 start)
8 /opt/QtPalmtop/bin/opieatd & 8 /opt/QtPalmtop/bin/opieatd &
9 ;; 9 ;;
10 stop) 10 stop)
11 killall opieatd 11 kill `cat /var/run/opieatd.pid`
12 ;; 12 ;;
13esac 13esac
14 14
15exit 0 15exit 0