* dcrt0.cc (do_exit): Rely on sigproc_terminate to set exit_state
appropriately. * pinfo.cc (pinfo::exit): Always call sigproc_terminate here. Rely on sigproc_terminate to signal signal thread to handle eventual process exit. * sigproc.cc (no_signals_available): Change criteria for determining if this process can handle signals to itself. (my_sendsig): New variable. Copy of my sendsig handle. (proc_can_be_signalled): Don't send signals if exit code is set. (sigproc_terminate): Use and set exit_state appropriately to determine when to do anything. Send __SIGEXIT to self to control process exit. (sig_send): Use my_sendsig for sending signals. Don't call proc_can_be_signalled for myself since the criteria is now different for sending signals to myself. (wait_sig): Copy myself->sendsig to my_sendsig for future use. Exit signal loop when __SIGEXIT is received. Wait for main thread to exit and use its exit status to actually exit process. * sigproc.h (__SIGEXIT): New enum. * dcrt0.cc (alloc_stack): Eliminate superfluous "return;". * debug.cc (add_handle): Ditto. * devices.in (device::parse): Ditto. * dtable.cc (dtable::vfork_parent_restore): Ditto. (dtable::vfork_child_fixup): Ditto. * environ.cc (parse_options): Ditto. * errno.cc (seterrno_from_win_error): Ditto. * exceptions.cc (sig_handle_tty_stop): Ditto. (set_signal_mask): Ditto. * fhandler.cc (fhandler_base::read): Ditto. (fhandler_base::operator delete): Ditto. (fhandler_base::seekdir): Ditto. (fhandler_base::rewinddir): Ditto. * fhandler_console.cc (fhandler_console::read): Ditto. (fhandler_console::fixup_after_exec): Ditto. * sigproc.cc (sigproc_init): Ditto. (sigproc_terminate): Ditto. * devices.cc: Regenerate.
This commit is contained in:
parent
00fb79f70e
commit
67483cb2cd
|
@ -1,3 +1,46 @@
|
|||
2005-09-13 Christopher Faylor <cgf@timesys.com>
|
||||
|
||||
* dcrt0.cc (do_exit): Rely on sigproc_terminate to set exit_state
|
||||
appropriately.
|
||||
* pinfo.cc (pinfo::exit): Always call sigproc_terminate here. Rely on
|
||||
sigproc_terminate to signal signal thread to handle eventual process
|
||||
exit.
|
||||
* sigproc.cc (no_signals_available): Change criteria for determining if
|
||||
this process can handle signals to itself.
|
||||
(my_sendsig): New variable. Copy of my sendsig handle.
|
||||
(proc_can_be_signalled): Don't send signals if exit code is set.
|
||||
(sigproc_terminate): Use and set exit_state appropriately to determine
|
||||
when to do anything. Send __SIGEXIT to self to control process exit.
|
||||
(sig_send): Use my_sendsig for sending signals. Don't call
|
||||
proc_can_be_signalled for myself since the criteria is now different
|
||||
for sending signals to myself.
|
||||
(wait_sig): Copy myself->sendsig to my_sendsig for future use. Exit
|
||||
signal loop when __SIGEXIT is received. Wait for main thread to exit
|
||||
and use its exit status to actually exit process.
|
||||
* sigproc.h (__SIGEXIT): New enum.
|
||||
|
||||
2005-09-13 Christopher Faylor <cgf@timesys.com>
|
||||
|
||||
* dcrt0.cc (alloc_stack): Eliminate superfluous "return;".
|
||||
* debug.cc (add_handle): Ditto.
|
||||
* devices.in (device::parse): Ditto.
|
||||
* dtable.cc (dtable::vfork_parent_restore): Ditto.
|
||||
(dtable::vfork_child_fixup): Ditto.
|
||||
* environ.cc (parse_options): Ditto.
|
||||
* errno.cc (seterrno_from_win_error): Ditto.
|
||||
* exceptions.cc (sig_handle_tty_stop): Ditto.
|
||||
(set_signal_mask): Ditto.
|
||||
* fhandler.cc (fhandler_base::read): Ditto.
|
||||
(fhandler_base::operator delete): Ditto.
|
||||
(fhandler_base::seekdir): Ditto.
|
||||
(fhandler_base::rewinddir): Ditto.
|
||||
* fhandler_console.cc (fhandler_console::read): Ditto.
|
||||
(fhandler_console::fixup_after_exec): Ditto.
|
||||
* sigproc.cc (sigproc_init): Ditto.
|
||||
(sigproc_terminate): Ditto.
|
||||
|
||||
* devices.cc: Regenerate.
|
||||
|
||||
2005-09-13 Christopher Faylor <cgf@timesys.com>
|
||||
|
||||
* sigproc.cc (wait_sig): Be more defensive about detecting when we're
|
||||
|
|
|
@ -518,8 +518,6 @@ alloc_stack (child_info_fork *ci)
|
|||
ci->stacksize = 0;
|
||||
else
|
||||
alloc_stack_hard_way (ci, b + sizeof (b) - 1);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef DEBUGGING
|
||||
|
@ -1059,10 +1057,7 @@ do_exit (int status)
|
|||
}
|
||||
|
||||
if (exit_state < ES_SIGPROCTERMINATE)
|
||||
{
|
||||
exit_state = ES_SIGPROCTERMINATE;
|
||||
sigproc_terminate ();
|
||||
}
|
||||
sigproc_terminate (); // sets exit_state directly
|
||||
|
||||
myself->stopsig = 0;
|
||||
if (exit_state < ES_TITLE)
|
||||
|
|
|
@ -153,8 +153,6 @@ add_handle (const char *func, int ln, HANDLE h, const char *name, bool inh)
|
|||
cygheap->debug.endh->next = hl;
|
||||
cygheap->debug.endh = hl;
|
||||
debug_printf ("protecting handle '%s', inherited flag %d", hl->name, hl->inherited);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
static void __stdcall
|
||||
|
|
|
@ -14899,7 +14899,6 @@ device::parse (_major_t major, _minor_t minor)
|
|||
|
||||
if (!*this)
|
||||
devn = FHDEV (major, minor);
|
||||
return;
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
@ -125,7 +125,6 @@ device::parse (_major_t major, _minor_t minor)
|
|||
|
||||
if (!*this)
|
||||
devn = FHDEV (major, minor);
|
||||
return;
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
@ -788,8 +788,6 @@ dtable::vfork_parent_restore ()
|
|||
cygheap->ctty->close (); // Undo previous bump of this archetype
|
||||
}
|
||||
cygheap->ctty_on_hold = NULL;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -824,8 +822,6 @@ dtable::vfork_child_fixup ()
|
|||
cygheap->ctty_on_hold->close ();
|
||||
cygheap->ctty_on_hold = NULL;
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
#endif /*NEWVFORK*/
|
||||
|
||||
|
|
|
@ -666,7 +666,6 @@ parse_options (char *buf)
|
|||
}
|
||||
}
|
||||
debug_printf ("returning");
|
||||
return;
|
||||
}
|
||||
|
||||
/* Set options from the registry. */
|
||||
|
|
|
@ -306,7 +306,6 @@ seterrno_from_win_error (const char *file, int line, DWORD code)
|
|||
{
|
||||
syscall_printf ("%s:%d windows error %d", file, line, code);
|
||||
set_errno (geterrno_from_win_error (code, EACCES));
|
||||
return;
|
||||
}
|
||||
|
||||
/* seterrno: Set `errno' based on GetLastError (). */
|
||||
|
|
|
@ -649,7 +649,6 @@ sig_handle_tty_stop (int sig)
|
|||
break;
|
||||
}
|
||||
_my_tls.incyg = 0;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1017,7 +1016,6 @@ set_signal_mask (sigset_t newmask, sigset_t& oldmask)
|
|||
else
|
||||
sigproc_printf ("not calling sig_dispatch_pending");
|
||||
mask_sync.release ();
|
||||
return;
|
||||
}
|
||||
|
||||
int __stdcall
|
||||
|
|
|
@ -789,7 +789,6 @@ fhandler_base::read (void *in_ptr, size_t& len)
|
|||
|
||||
out:
|
||||
debug_printf ("returning %d, %s mode", len, rbinary () ? "binary" : "text");
|
||||
return;
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -1398,7 +1397,6 @@ void
|
|||
fhandler_base::operator delete (void *p)
|
||||
{
|
||||
cfree (p);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Normal I/O constructor */
|
||||
|
@ -1555,14 +1553,12 @@ void
|
|||
fhandler_base::seekdir (DIR *, _off64_t)
|
||||
{
|
||||
set_errno (ENOTDIR);
|
||||
return;
|
||||
}
|
||||
|
||||
void
|
||||
fhandler_base::rewinddir (DIR *)
|
||||
{
|
||||
set_errno (ENOTDIR);
|
||||
return;
|
||||
}
|
||||
|
||||
int
|
||||
|
|
|
@ -546,7 +546,6 @@ err:
|
|||
sig_exit:
|
||||
set_sig_errno (EINTR);
|
||||
buflen = (size_t) -1;
|
||||
return;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1824,5 +1823,4 @@ fhandler_console::fixup_after_exec ()
|
|||
|
||||
CloseHandle (h);
|
||||
CloseHandle (oh);
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -136,13 +136,12 @@ pinfo::zap_cwd ()
|
|||
void
|
||||
pinfo::exit (DWORD n)
|
||||
{
|
||||
sigproc_terminate ();
|
||||
exit_state = ES_FINAL;
|
||||
|
||||
cygthread::terminate ();
|
||||
if (n != EXITCODE_NOSET)
|
||||
{
|
||||
sigproc_terminate (); /* Just terminate signal and process stuff */
|
||||
self->exitcode = EXITCODE_SET | n;/* We're really exiting. Record the UNIX exit code. */
|
||||
}
|
||||
self->exitcode = EXITCODE_SET | n;/* We're really exiting. Record the UNIX exit code. */
|
||||
|
||||
/* FIXME: There is a potential race between an execed process and its
|
||||
parent here. I hated to add a mutex just for this, though. */
|
||||
|
@ -161,12 +160,25 @@ pinfo::exit (DWORD n)
|
|||
int exitcode = self->exitcode & 0xffff;
|
||||
if (!self->cygstarted)
|
||||
exitcode >>= 8;
|
||||
release ();
|
||||
|
||||
_my_tls.stacklock = 0;
|
||||
_my_tls.stackptr = _my_tls.stack;
|
||||
sigproc_printf ("Calling ExitProcess hProcess %p, n %p, exitcode %p",
|
||||
if (&_my_tls == _main_tls)
|
||||
{
|
||||
sigproc_printf ("Calling ExitProcess hProcess %p, n %p, exitcode %p",
|
||||
hProcess, n, exitcode);
|
||||
ExitThread (exitcode);
|
||||
}
|
||||
else if (hMainThread)
|
||||
{
|
||||
sigproc_printf ("Calling TerminateThread since %p != %p, %p, n %p, exitcode %p",
|
||||
&_my_tls, _main_tls, hProcess, n, exitcode);
|
||||
TerminateThread (hMainThread, exitcode);
|
||||
}
|
||||
|
||||
sigproc_printf ("Calling ExitProcess since hMainthread is 0, hProcess %p, n %p, exitcode %p",
|
||||
hProcess, n, exitcode);
|
||||
release ();
|
||||
ExitProcess (exitcode);
|
||||
}
|
||||
# undef self
|
||||
|
|
|
@ -38,7 +38,7 @@ details. */
|
|||
#define WSSC 60000 // Wait for signal completion
|
||||
#define WPSP 40000 // Wait for proc_subproc mutex
|
||||
|
||||
#define no_signals_available() (!hwait_sig || (myself->sendsig == INVALID_HANDLE_VALUE) || exit_state)
|
||||
#define no_signals_available() (!hwait_sig || (myself->exitcode & EXITCODE_SET) && !my_sendsig)
|
||||
|
||||
#define NPROCS 256
|
||||
|
||||
|
@ -80,6 +80,7 @@ static __inline__ bool get_proc_lock (DWORD, DWORD);
|
|||
static bool __stdcall remove_proc (int);
|
||||
static bool __stdcall stopped_or_terminated (waitq *, _pinfo *);
|
||||
static DWORD WINAPI wait_sig (VOID *arg);
|
||||
static HANDLE NO_COPY my_sendsig;
|
||||
|
||||
/* wait_sig bookkeeping */
|
||||
|
||||
|
@ -166,7 +167,7 @@ get_proc_lock (DWORD what, DWORD val)
|
|||
static bool __stdcall
|
||||
proc_can_be_signalled (_pinfo *p)
|
||||
{
|
||||
if (p->sendsig != INVALID_HANDLE_VALUE)
|
||||
if (!(p->exitcode & EXITCODE_SET))
|
||||
{
|
||||
if (p == myself_nowait || p == myself)
|
||||
if (hwait_sig)
|
||||
|
@ -428,7 +429,6 @@ sig_clear (int target_sig)
|
|||
}
|
||||
sigq.restore (save);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
extern "C" int
|
||||
|
@ -493,7 +493,6 @@ sigproc_init ()
|
|||
|
||||
global_sigs[SIGSTOP].sa_flags = SA_RESTART | SA_NODEFER;
|
||||
sigproc_printf ("process/signal handling enabled(%x)", myself->process_state);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Called on process termination to terminate signal and process threads.
|
||||
|
@ -501,23 +500,15 @@ sigproc_init ()
|
|||
void __stdcall
|
||||
sigproc_terminate (void)
|
||||
{
|
||||
hwait_sig = NULL;
|
||||
|
||||
if (myself->sendsig == INVALID_HANDLE_VALUE)
|
||||
sigproc_printf ("sigproc handling not active");
|
||||
if (exit_state > ES_SIGPROCTERMINATE)
|
||||
sigproc_printf ("already performed");
|
||||
else
|
||||
{
|
||||
exit_state = ES_SIGPROCTERMINATE;
|
||||
sigproc_printf ("entering");
|
||||
if (!hExeced)
|
||||
{
|
||||
HANDLE sendsig = myself->sendsig;
|
||||
myself->sendsig = INVALID_HANDLE_VALUE;
|
||||
CloseHandle (sendsig);
|
||||
}
|
||||
sig_send (myself_nowait, __SIGEXIT);
|
||||
proc_terminate (); // clean up process stuff
|
||||
}
|
||||
proc_terminate (); // clean up process stuff
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
int __stdcall
|
||||
|
@ -545,7 +536,18 @@ sig_send (_pinfo *p, siginfo_t& si, _cygtls *tls)
|
|||
pack.wakeup = NULL;
|
||||
bool wait_for_completion;
|
||||
if (!(its_me = (p == NULL || p == myself || p == myself_nowait)))
|
||||
wait_for_completion = false;
|
||||
{
|
||||
/* It is possible that the process is not yet ready to receive messages
|
||||
* or that it has exited. Detect this.
|
||||
*/
|
||||
if (!proc_can_be_signalled (p)) /* Is the process accepting messages? */
|
||||
{
|
||||
sigproc_printf ("invalid pid %d(%x), signal %d",
|
||||
p->pid, p->process_state, si.si_signo);
|
||||
goto out;
|
||||
}
|
||||
wait_for_completion = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (no_signals_available ())
|
||||
|
@ -561,18 +563,9 @@ sig_send (_pinfo *p, siginfo_t& si, _cygtls *tls)
|
|||
p = myself;
|
||||
}
|
||||
|
||||
/* It is possible that the process is not yet ready to receive messages
|
||||
* or that it has exited. Detect this.
|
||||
*/
|
||||
if (!proc_can_be_signalled (p)) /* Is the process accepting messages? */
|
||||
{
|
||||
sigproc_printf ("invalid pid %d(%x), signal %d",
|
||||
p->pid, p->process_state, si.si_signo);
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (its_me)
|
||||
sendsig = myself->sendsig;
|
||||
sendsig = my_sendsig;
|
||||
else
|
||||
{
|
||||
HANDLE dupsig;
|
||||
|
@ -1005,6 +998,7 @@ wait_sig (VOID *self)
|
|||
if (!CreatePipe (&readsig, &myself->sendsig, sec_user_nih (sa_buf), 0))
|
||||
api_fatal ("couldn't create signal pipe, %E");
|
||||
sigCONT = CreateEvent (&sec_none_nih, FALSE, FALSE, NULL);
|
||||
my_sendsig = myself->sendsig;
|
||||
|
||||
/* Setting dwProcessId flags that this process is now capable of receiving
|
||||
signals. Prior to this, dwProcessId was set to the windows pid of
|
||||
|
@ -1028,7 +1022,7 @@ wait_sig (VOID *self)
|
|||
sigpacket pack;
|
||||
if (!ReadFile (readsig, &pack, sizeof (pack), &nb, NULL))
|
||||
break;
|
||||
if (exit_state || myself->sendsig == INVALID_HANDLE_VALUE)
|
||||
if (exit_state || pack.si.si_signo == __SIGEXIT)
|
||||
break;
|
||||
|
||||
if (nb != sizeof (pack))
|
||||
|
@ -1128,6 +1122,16 @@ wait_sig (VOID *self)
|
|||
}
|
||||
}
|
||||
|
||||
my_sendsig = NULL;
|
||||
sigproc_printf ("done");
|
||||
if (WaitForSingleObject (hMainThread, 5000) == WAIT_OBJECT_0)
|
||||
{
|
||||
DWORD exitcode = 1;
|
||||
myself.release ();
|
||||
GetExitCodeThread (hMainThread, &exitcode);
|
||||
sigproc_printf ("Calling ExitProcess, exitcode %p",
|
||||
exitcode);
|
||||
ExitProcess (exitcode);
|
||||
}
|
||||
ExitThread (0);
|
||||
}
|
||||
|
|
|
@ -22,7 +22,8 @@ enum
|
|||
__SIGDELETE = -(NSIG + 5),
|
||||
__SIGFLUSHFAST = -(NSIG + 6),
|
||||
__SIGHOLD = -(NSIG + 7),
|
||||
__SIGNOHOLD = -(NSIG + 8)
|
||||
__SIGNOHOLD = -(NSIG + 8),
|
||||
__SIGEXIT = -(NSIG + 9)
|
||||
};
|
||||
#endif
|
||||
|
||||
|
|
Loading…
Reference in New Issue