Blob


1 #include <signal.h>
2 #include "threadimpl.h"
4 typedef struct Mainarg Mainarg;
5 struct Mainarg
6 {
7 int argc;
8 char **argv;
9 };
11 int mainstacksize;
12 int _threadnotefd;
13 int _threadpasserpid;
14 static void mainlauncher(void*);
15 extern void (*_sysfatal)(char*, va_list);
17 void
18 _threadstatus(int x)
19 {
20 USED(x);
21 threadstatus();
22 }
24 void
25 _threaddie(int x)
26 {
27 extern char *_threadexitsallstatus;
28 USED(x);
30 if(_threadexitsallstatus)
31 exit(_threadexitsallstatus[0] ? 1 : 0);
32 }
34 static void
35 _nop(int x)
36 {
37 USED(x);
38 }
40 int
41 main(int argc, char **argv)
42 {
43 Mainarg *a;
44 Proc *p;
46 signal(SIGTERM, _threaddie);
47 signal(SIGCHLD, _nop);
48 // signal(SIGINFO, _threadstatus);
49 // rfork(RFREND);
51 //_threaddebuglevel = (DBGSCHED|DBGCHAN|DBGREND)^~0;
52 _systhreadinit();
53 _qlockinit(_threadrendezvous);
54 _sysfatal = _threadsysfatal;
55 notify(_threadnote);
56 if(mainstacksize == 0)
57 mainstacksize = 32*1024;
59 a = _threadmalloc(sizeof *a, 1);
60 a->argc = argc;
61 a->argv = argv;
63 p = _newproc(mainlauncher, a, mainstacksize, "threadmain", 0, 0);
64 _schedinit(p);
65 abort(); /* not reached */
66 return 0;
67 }
69 static void
70 mainlauncher(void *arg)
71 {
72 Mainarg *a;
74 a = arg;
75 threadmain(a->argc, a->argv);
76 threadexits("threadmain");
77 }
79 void
80 _threadsignal(void)
81 {
82 }
84 void
85 _threadsignalpasser(void)
86 {
87 }
89 int
90 _schedfork(Proc *p)
91 {
92 int pid;
93 lock(&p->lock);
94 pid = ffork(RFMEM|RFNOWAIT, _schedinit, p);
95 p->pid = pid;
96 unlock(&p->lock);
97 return pid;
99 }
101 void
102 _schedexit(Proc *p)
104 char ex[ERRMAX];
105 Proc **l;
107 lock(&_threadpq.lock);
108 for(l=&_threadpq.head; *l; l=&(*l)->next){
109 if(*l == p){
110 *l = p->next;
111 if(*l == nil)
112 _threadpq.tail = l;
113 break;
116 _threadprocs--;
117 unlock(&_threadpq.lock);
119 strncpy(ex, p->exitstr, sizeof ex);
120 ex[sizeof ex-1] = '\0';
121 free(p);
122 _exit(ex[0]);
125 int
126 nrand(int n)
128 return random()%n;
131 void
132 _systhreadinit(void)
136 void
137 threadstats(void)
139 extern int _threadnrendez, _threadhighnrendez,
140 _threadnalt, _threadhighnentry;
141 fprint(2, "*** THREAD LIBRARY STATS ***\n");
142 fprint(2, "nrendez %d high simultaneous %d\n",
143 _threadnrendez, _threadhighnrendez);
144 fprint(2, "nalt %d high simultaneous entry %d\n",
145 _threadnalt, _threadhighnentry);