Close stdin, stdout, and stderr, even if no files specified.
[detach.git] / detach.c
blobc1075c74266469d75fcdfd2a89c9131ce88ac0e9
1 #include <stdio.h>
2 #include <sys/types.h>
3 #include <unistd.h>
4 #include <fcntl.h>
5 #include <string.h>
7 #ifndef NULL
8 #define NULL ((void*) 0)
9 #endif
11 static void replacefd(int fd, const char *filename, int flags, int mode) {
12 int n;
13 n = open(filename, flags, mode);
14 if(n < 0) {
15 perror(filename);
16 exit(1);
17 } else {
18 dup2(n, fd);
19 close(n);
23 int main(int argc, char **argv) {
24 int do_fork = 1, command_start, i;
25 char *infile = NULL, *outfile = NULL, *errfile = NULL, *pidfile = NULL;
26 FILE *pidfh;
28 /* Parse command line */
29 for(i = 1; i < argc; i++) {
30 if(!strcmp(argv[i], "-e")) errfile = argv[++i];
31 else if(!strcmp(argv[i], "-f")) do_fork = 0;
32 else if(!strcmp(argv[i], "-i")) infile = argv[++i];
33 else if(!strcmp(argv[i], "-o")) outfile = argv[++i];
34 else if(!strcmp(argv[i], "-p")) pidfile = argv[++i];
35 else if(!strcmp(argv[i], "--")) {
36 i++;
37 break;
38 } else if(argv[i][0] == '-') {
39 fprintf(stderr, "Invalid option: %s\n", argv[i]);
40 exit(0x80);
41 } else break;
43 command_start = i;
45 if(do_fork && fork()) return 0;
47 if(pidfile) {
48 pidfh = fopen(pidfile, "w");
49 if(!pidfh) {
50 perror(pidfile);
51 exit(1);
53 fprintf(pidfh, "%d\n", getpid());
54 fclose(pidfh);
57 if(infile) replacefd(0, infile, O_RDONLY, 0666);
58 else close(0);
59 if(outfile) replacefd(1, outfile, O_WRONLY | O_CREAT | O_TRUNC, 0666);
60 else close(1);
61 if(errfile) replacefd(2, errfile, O_WRONLY | O_CREAT | O_TRUNC, 0666);
62 else close(2);
63 setsid();
65 execvp(argv[command_start], &argv[command_start]);
67 perror(argv[command_start]);
68 return -1;