diff options
author | Jason Downs <downsj@cvs.openbsd.org> | 1996-08-19 20:09:10 +0000 |
---|---|---|
committer | Jason Downs <downsj@cvs.openbsd.org> | 1996-08-19 20:09:10 +0000 |
commit | e7e852656e3beb5f62f8c146ba24004cfda2cf88 (patch) | |
tree | b312bc3e985b3f1cf19691c779e7870219573b6e /bin/ksh/jobs.c | |
parent | 1e9e82f84b5de8bcd110c41c780f476397c385d9 (diff) |
update to pdksh-5.2.8
Diffstat (limited to 'bin/ksh/jobs.c')
-rw-r--r-- | bin/ksh/jobs.c | 77 |
1 files changed, 46 insertions, 31 deletions
diff --git a/bin/ksh/jobs.c b/bin/ksh/jobs.c index d40a092ac4b..e1c11fcd04a 100644 --- a/bin/ksh/jobs.c +++ b/bin/ksh/jobs.c @@ -1,4 +1,4 @@ -/* $OpenBSD: jobs.c,v 1.1 1996/08/14 06:19:11 downsj Exp $ */ +/* $OpenBSD: jobs.c,v 1.2 1996/08/19 20:08:52 downsj Exp $ */ /* * Process and job control @@ -140,6 +140,7 @@ struct job { clock_t usrtime; /* user time used by job */ Proc *proc_list; /* process list */ Proc *last_proc; /* last process in list */ + Coproc_id coproc_id; /* 0 or id of coprocess output pipe */ #ifdef TTY_PGRP TTY_state ttystate; /* saved tty state for stopped jobs */ #endif /* TTY_PGRP */ @@ -177,7 +178,6 @@ static int child_max; /* CHILD_MAX */ #ifdef JOB_SIGS -static sigset_t sm_default, sm_sigchld; /* held_sigchld is set if sigchld occurs before a job is completely started */ static int held_sigchld; #endif /* JOB_SIGS */ @@ -234,7 +234,8 @@ j_init(mflagset) sigemptyset(&sm_sigchld); sigaddset(&sm_sigchld, SIGCHLD); - setsig(&sigtraps[SIGCHLD], j_sigchld, SS_RESTORE_ORIG|SS_FORCE); + setsig(&sigtraps[SIGCHLD], j_sigchld, + SS_RESTORE_ORIG|SS_FORCE|SS_SHTRAP); #else /* JOB_SIGS */ /* Make sure SIGCHLD isn't ignored - can do odd things under SYSV */ setsig(&sigtraps[SIGCHLD], SIG_DFL, SS_RESTORE_ORIG|SS_FORCE); @@ -253,9 +254,12 @@ j_init(mflagset) if (Flag(FMONITOR) || Flag(FTALKING)) { int i; - /* j_change() sets these to SS_RESTORE_DFL if FMONITOR */ + /* the TF_SHELL_USES test is a kludge that lets us know if + * if the signals have been changed by the shell. + */ for (i = NELEM(tt_sigs); --i >= 0; ) { sigtraps[tt_sigs[i]].flags |= TF_SHELL_USES; + /* j_change() sets this to SS_RESTORE_DFL if FMONITOR */ setsig(&sigtraps[tt_sigs[i]], SIG_IGN, SS_RESTORE_IGN|SS_FORCE); } @@ -397,9 +401,6 @@ j_change() } else { # ifdef TTY_PGRP ttypgrp_ok = 0; - /* the TF_SHELL_USES test is a kludge that lets us know if - * if the signals have been changed by the shell. - */ if (Flag(FTALKING)) for (i = NELEM(tt_sigs); --i >= 0; ) setsig(&sigtraps[tt_sigs[i]], SIG_IGN, @@ -410,7 +411,7 @@ j_change() |TF_ORIG_DFL)) setsig(&sigtraps[tt_sigs[i]], (sigtraps[tt_sigs[i]].flags & TF_ORIG_IGN) ? SIG_IGN : SIG_DFL, - SS_RESTORE_CURR|SS_FORCE); + SS_RESTORE_ORIG|SS_FORCE); } # endif /* TTY_PGRP */ if (!Flag(FTALKING)) @@ -483,12 +484,9 @@ exchild(t, flags, close_fd) j->ppid = procpid; j->age = ++njobs; j->proc_list = p; + j->coproc_id = 0; last_job = j; last_proc = p; - if (flags & XXCOM) - j->flags |= JF_XXCOM; - else if (!(flags & XBGND)) - j->flags |= JF_FG; put_job(j, PJ_PAST_STOPPED); } @@ -535,8 +533,8 @@ exchild(t, flags, close_fd) dotty = 1; # ifdef NEED_PGRP_SYNC if (j_sync_open) { - close(j_sync_pipe[ischild ? 1 : 0]); - j_sync_pipe[ischild ? 1 : 0] = -1; + close(j_sync_pipe[ischild]); + j_sync_pipe[ischild] = -1; dosync = ischild; } # endif /* NEED_PGRP_SYNC */ @@ -571,18 +569,19 @@ exchild(t, flags, close_fd) #endif /* JOBS */ /* used to close pipe input fd */ - if (close_fd >= 0 && (((orig_flags & XPCLOSE) && i != 0) - || ((orig_flags & XCCLOSE) && i == 0))) + if (close_fd >= 0 && (((orig_flags & XPCLOSE) && !ischild) + || ((orig_flags & XCCLOSE) && ischild))) close(close_fd); - if (i == 0) { /* child */ + if (ischild) { /* child */ +#ifdef KSH + /* Do this before restoring signal */ + if (orig_flags & XCOPROC) + coproc_cleanup(FALSE); +#endif /* KSH */ #ifdef JOB_SIGS sigprocmask(SIG_SETMASK, &omask, (sigset_t *) 0); #endif /* JOB_SIGS */ cleanup_parents_env(); -#ifdef KSH - if (orig_flags & XCOPROC) - cleanup_coproc(FALSE); -#endif /* KSH */ #ifdef TTY_PGRP /* If FMONITOR or FTALKING is set, these signals are ignored, * if neither FMONITOR nor FTALKING are set, the signals have @@ -604,9 +603,9 @@ exchild(t, flags, close_fd) setsig(&sigtraps[SIGQUIT], SIG_IGN, SS_RESTORE_IGN|SS_FORCE); if (!(orig_flags & (XPIPEI | XCOPROC))) { - i = open("/dev/null", 0); - (void) ksh_dup2(i, 0, TRUE); - close(i); + int fd = open("/dev/null", 0); + (void) ksh_dup2(fd, 0, TRUE); + close(fd); } } remove_job(j, "child"); /* in case of `jobs` command */ @@ -634,8 +633,11 @@ exchild(t, flags, close_fd) #endif /* TTY_PGRP */ j_startjob(j); #ifdef KSH - if (flags & XCOPROC) - coproc.job = (void *) j; + if (orig_flags & XCOPROC) { + j->coproc_id = coproc.id; + coproc.njobs++; /* n jobs using co-process output */ + coproc.job = (void *) j; /* j using co-process input */ + } #endif /* KSH */ if (flags & XBGND) { j_set_async(j); @@ -1268,8 +1270,6 @@ j_sigchld(sig) WAIT_T status; struct tms t0, t1; - trapsig(sig); - #ifdef JOB_SIGS /* Don't wait for any processes if a job is partially started. * This is so we don't do away with the process group leader @@ -1386,9 +1386,24 @@ check_job(j) * remove_job() since neither may be called for non-interactive * shells. */ - if ((j->state == PEXITED || j->state == PSIGNALLED) - && coproc.job == (void *) j) - coproc.job = (void *) 0; + if (j->state == PEXITED || j->state == PSIGNALLED) { + /* No need to keep co-process input any more + * (at leasst, this is what ksh93d thinks) + */ + if (coproc.job == j) { + coproc.job = (void *) 0; + /* XXX would be nice to get the closes out of here + * so they aren't done in the signal handler. + * Would mean a check in coproc_getfd() to + * do "if job == 0 && write >= 0, close write". + */ + coproc_write_close(coproc.write); + } + /* Do we need to keep the output? */ + if (j->coproc_id && j->coproc_id == coproc.id + && --coproc.njobs == 0) + coproc_readw_close(coproc.read); + } #endif /* KSH */ j->flags |= JF_CHANGED; |