]> arthur.barton.de Git - netatalk.git/blob - libatalk/util/server_lock.c
2a5d43dc12d3f394b6cb632b388c6f30d7208624
[netatalk.git] / libatalk / util / server_lock.c
1 /*
2  * Copyright (c) 1997 Adrian Sun (asun@zoology.washington.edu)
3  * All rights reserved. See COPYRIGHT.
4  *
5  * Copyright (c) 1990,1993 Regents of The University of Michigan.
6  * All Rights Reserved.  See COPYRIGHT.
7  */
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <string.h>
11 #include <unistd.h>
12 #include <fcntl.h>
13 #include <termios.h>
14 #include <sys/ioctl.h>
15 #include <sys/types.h>
16 #include <sys/stat.h>
17 #include <errno.h>
18
19 #include <atalk/compat.h>
20 #include <atalk/util.h>
21
22 /* this creates an open lock file which hangs around until the program
23  * dies. it returns the pid. due to problems w/ solaris, this has
24  * been changed to do the kill() thing. */
25 pid_t server_lock(char *program, char *pidfile, int debug)
26 {
27   char buf[10];
28   FILE *pf;
29   pid_t pid;
30   int mask;
31   
32   mask = umask(022);
33   /* check for pid. this can get fooled by stale pid's. */
34   if ((pf = fopen(pidfile, "r"))) {
35     if (fgets(buf, sizeof(buf), pf) && !kill(pid = atol(buf), 0)) {
36       fprintf( stderr, "%s is already running (pid = %d), or the lock file is stale.\n",
37                program, pid);      
38       fclose(pf);
39       return -1;
40     }
41     fclose(pf);
42   }
43
44   if ((pf = fopen(pidfile, "w")) == NULL) {
45     fprintf(stderr, "%s: can't open lock file, \"%s\"\n", program,
46             pidfile);
47     return -1;
48   }
49   umask(mask);
50
51   /*
52    * Disassociate from controlling tty.
53    */
54   if ( !debug ) {
55     int         i;
56
57     switch (pid = fork()) {
58     case 0 :
59       fclose(stdin);
60       fclose(stdout);
61       fclose(stderr);
62
63       if (( i = open( "/dev/tty", O_RDWR )) >= 0 ) {
64         (void)ioctl( i, TIOCNOTTY, 0 );
65         setpgid( 0, getpid());
66         (void) close(i);
67       }
68       break;
69     case -1 :  /* error */
70       perror( "fork" );
71     default :  /* server */
72       fclose(pf);
73       return pid;
74     }
75   } 
76
77   fprintf(pf, "%d\n", getpid());
78   fclose(pf);
79   return 0;
80 }