commit - e8a7b9699925f3f650593d07eb382155e9374ae6
commit + e127e40bb1327662a05f5b70dd1bbca5c69b042c
blob - 2cbb443729dde56b7af17a6e338ee32de1c2d459
blob + f31b004ad2099c50b0b2840210e0a5da05f35f7e
--- src/libthread/exec.c
+++ src/libthread/exec.c
static Lock thewaitlock;
static Channel *thewaitchan;
static Channel *dowaitchan;
+static Channel *execchan;
-/* BUG - start waitproc on first exec, not when threadwaitchan is called */
static void
waitproc(void *v)
{
Channel *c;
Waitmsg *w;
+ Execjob *e;
_threadsetsysproc();
for(;;){
- while((w = wait()) == nil){
+ for(;;){
+ while((e = nbrecvp(execchan)) != nil)
+ sendul(e->c, _threadspawn(e->fd, e->cmd, e->argv));
+ if((w = wait()) != nil)
+ break;
if(errno == ECHILD)
recvul(dowaitchan);
}
}
thewaitchan = chancreate(sizeof(Waitmsg*), 4);
chansetname(thewaitchan, "threadwaitchan");
- dowaitchan = chancreate(sizeof(ulong), 1);
- chansetname(dowaitchan, "dowaitchan");
- proccreate(waitproc, nil, STACK);
unlock(&thewaitlock);
return thewaitchan;
}
int
-threadspawn(int fd[3], char *cmd, char *argv[])
+_threadspawn(int fd[3], char *cmd, char *argv[])
{
int i, n, p[2], pid;
char exitstr[100];
}
int
+threadspawn(int fd[3], char *cmd, char *argv[])
+{
+ if(dowaitchan == nil){
+ lock(&thewaitlock);
+ if(dowaitchan == nil){
+ dowaitchan = chancreate(sizeof(ulong), 1);
+ chansetname(dowaitchan, "dowaitchan");
+ execchan = chancreate(sizeof(void*), 0);
+ chansetname(execchan, "execchan");
+ proccreate(waitproc, nil, STACK);
+ }
+ unlock(&thewaitlock);
+ }
+ return _runthreadspawn(fd, cmd, argv);
+}
+
+
+int
_threadexec(Channel *cpid, int fd[3], char *cmd, char *argv[])
{
int pid;
blob - 2ddd8c72777c7d410ba56c615e54b4725aa727bb
blob + e1fed2bff4a43749abe88446e367ba5254e32ced
--- src/libthread/pthread.c
+++ src/libthread/pthread.c
pthread_key_create(&prockey, 0);
}
+int
+_runthreadspawn(int *fd, char *cmd, char **argv)
+{
+ return _threadspawn(fd, cmd, argv);
+}
+
blob - d30d58b6e5a1ab1fde33970803c7a4211dae847d
blob + 9f0a53d520a34727cbd144a540bd7934a7808a23
--- src/libthread/threadimpl.h
+++ src/libthread/threadimpl.h
#include <ucontext.h>
typedef struct Context Context;
+typedef struct Execjob Execjob;
typedef struct Proc Proc;
typedef struct _Procrendez _Procrendez;
ucontext_t uc;
};
+struct Execjob
+{
+ int *fd;
+ char *cmd;
+ char **argv;
+ Channel *c;
+};
+
struct _Thread
{
_Thread *next;
extern int _threadlock(Lock*, int, ulong);
extern void _threadunlock(Lock*, ulong);
extern void _pthreadinit(void);
+extern int _threadspawn(int*, char*, char**);
+extern int _runthreadspawn(int*, char*, char**);