1 ddb664da 2004-12-28 devnull #include "threadimpl.h"
3 ddb664da 2004-12-28 devnull #undef pipe
4 ddb664da 2004-12-28 devnull #undef wait
6 ddb664da 2004-12-28 devnull static int sigpid;
7 ddb664da 2004-12-28 devnull static int threadpassfd;
9 ddb664da 2004-12-28 devnull static void
10 ddb664da 2004-12-28 devnull child(void)
12 1d2533d0 2004-12-28 devnull int status, pid;
13 1d2533d0 2004-12-28 devnull pid = wait(&status);
14 1d2533d0 2004-12-28 devnull if(pid < 0)
15 1d2533d0 2004-12-28 devnull fprint(2, "wait: %r\n");
16 1d2533d0 2004-12-28 devnull else if(WIFEXITED(status))
17 1d2533d0 2004-12-28 devnull _exit(WEXITSTATUS(status));
18 1d2533d0 2004-12-28 devnull print("pid %d if %d %d\n", pid, WIFEXITED(status), WEXITSTATUS(status));
19 d54ead7f 2004-12-28 devnull _exit(97);
22 ddb664da 2004-12-28 devnull static void
23 ddb664da 2004-12-28 devnull sigpass(int sig)
25 ddb664da 2004-12-28 devnull if(sig == SIGCHLD)
28 ddb664da 2004-12-28 devnull kill(sigpid, sig);
32 ddb664da 2004-12-28 devnull _threadsetupdaemonize(void)
34 ddb664da 2004-12-28 devnull int i, n, pid;
35 ddb664da 2004-12-28 devnull int p[2];
36 ddb664da 2004-12-28 devnull char buf[20];
38 ddb664da 2004-12-28 devnull sigpid = 1;
40 ddb664da 2004-12-28 devnull threadlinklibrary();
42 ddb664da 2004-12-28 devnull if(pipe(p) < 0)
43 ddb664da 2004-12-28 devnull sysfatal("passer pipe: %r");
45 ddb664da 2004-12-28 devnull /* hide these somewhere they won't cause harm */
46 ddb664da 2004-12-28 devnull if(dup(p[0], 98) < 0 || dup(p[1], 99) < 0)
47 ddb664da 2004-12-28 devnull sysfatal("passer pipe dup: %r");
48 ddb664da 2004-12-28 devnull close(p[0]);
49 ddb664da 2004-12-28 devnull close(p[1]);
50 ddb664da 2004-12-28 devnull p[0] = 98;
51 ddb664da 2004-12-28 devnull p[1] = 99;
53 ddb664da 2004-12-28 devnull /* close on exec */
54 ddb664da 2004-12-28 devnull if(fcntl(p[0], F_SETFD, 1) < 0 || fcntl(p[1], F_SETFD, 1) < 0)
55 ddb664da 2004-12-28 devnull sysfatal("passer pipe pipe fcntl: %r");
57 1d2533d0 2004-12-28 devnull signal(SIGCHLD, sigpass);
58 ddb664da 2004-12-28 devnull switch(pid = fork()){
60 ddb664da 2004-12-28 devnull sysfatal("passer fork: %r");
62 ddb664da 2004-12-28 devnull close(p[1]);
65 1d2533d0 2004-12-28 devnull signal(SIGCHLD, SIG_DFL);
66 ddb664da 2004-12-28 devnull rfork(RFNOTEG);
67 ddb664da 2004-12-28 devnull close(p[0]);
68 ddb664da 2004-12-28 devnull threadpassfd = p[1];
72 ddb664da 2004-12-28 devnull sigpid = pid;
73 ddb664da 2004-12-28 devnull for(i=0; i<NSIG; i++){
74 ddb664da 2004-12-28 devnull struct sigaction sa;
76 ddb664da 2004-12-28 devnull memset(&sa, 0, sizeof sa);
77 ddb664da 2004-12-28 devnull sa.sa_handler = sigpass;
78 ddb664da 2004-12-28 devnull sa.sa_flags |= SA_RESTART;
79 ddb664da 2004-12-28 devnull sigaction(i, &sa, nil);
83 ddb664da 2004-12-28 devnull n = read(p[0], buf, sizeof buf-1);
84 ddb664da 2004-12-28 devnull if(n == 0) /* program exited */
86 ddb664da 2004-12-28 devnull if(n > 0)
88 d54ead7f 2004-12-28 devnull print("passer read: %r\n");
90 ddb664da 2004-12-28 devnull buf[n] = 0;
91 ddb664da 2004-12-28 devnull _exit(atoi(buf));
95 ddb664da 2004-12-28 devnull threaddaemonize(void)
97 1d2533d0 2004-12-28 devnull if(threadpassfd >= 0){
98 1d2533d0 2004-12-28 devnull write(threadpassfd, "0", 1);
99 1d2533d0 2004-12-28 devnull close(threadpassfd);
100 1d2533d0 2004-12-28 devnull threadpassfd = -1;