Welcome to mirror list, hosted at ThFree Co, Russian Federation.

cygwin.com/git/newlib-cygwin.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristopher Faylor <me@cgf.cx>2004-02-26 08:10:49 +0300
committerChristopher Faylor <me@cgf.cx>2004-02-26 08:10:49 +0300
commitca713cfab35fe144b73240ebe2c333c36fd7a214 (patch)
treefea3c6ad34283801c717108aae1f7ff6729f0b92 /winsup/cygwin/signal.cc
parentf9e19c093165d7c75bd9d04204845ed53b8ff0a8 (diff)
* exceptions.cc (setup_handler): Signal event for any sigwaitinfo if it exists
to force signal to be handled. Zero event here to prevent races. * signal.cc (sigwaitinfo): Use local handle value for everything since signal thread could zero event element at any time. Detect when awaking due to thread not in mask and set return value and errno accordingly. Don't set signal number to zero unless we've recognized the signal. * sigproc.cc (sigq): Rename from sigqueue throughout. * thread.cc (pthread::join): Handle signals received while waiting for thread to terminate. * cygwin.din: Export sighold, sigqueue. * exceptions.cc (sighold): Define new function. * signal.cc (handle_sigprocmask): Set correct errno for invalid signal. Simplify debugging output. (sigqueue): Define new function. * include/cygwin/signal.h (sighold): Declare new function. (sigqueue): Ditto. * include/cygwin/version.h: Bump API minor version number. * include/limits.h (TIMER_MAX): Define. (_POSIX_TIMER_MAX): Ditto.
Diffstat (limited to 'winsup/cygwin/signal.cc')
-rw-r--r--winsup/cygwin/signal.cc46
1 files changed, 35 insertions, 11 deletions
diff --git a/winsup/cygwin/signal.cc b/winsup/cygwin/signal.cc
index b0ac94a79..52c402c49 100644
--- a/winsup/cygwin/signal.cc
+++ b/winsup/cygwin/signal.cc
@@ -141,8 +141,8 @@ handle_sigprocmask (int sig, const sigset_t *set, sigset_t *oldset, sigset_t& op
/* check that sig is in right range */
if (sig < 0 || sig >= NSIG)
{
- set_errno (ESRCH);
- syscall_printf ("SIG_ERR = sigprocmask signal %d out of range", sig);
+ set_errno (EINVAL);
+ syscall_printf ("signal %d out of range", sig);
return -1;
}
@@ -493,30 +493,54 @@ sigwaitinfo (const sigset_t *set, siginfo_t *info)
pthread_testcancel ();
HANDLE h;
h = _my_tls.event = CreateEvent (&sec_none_nih, FALSE, FALSE, NULL);
- if (!_my_tls.event)
+ if (!h)
{
__seterrno ();
return -1;
}
_my_tls.sigwait_mask = *set;
+ sig_dispatch_pending (true);
int res;
- switch (WaitForSingleObject (_my_tls.event, INFINITE))
+ switch (WaitForSingleObject (h, INFINITE))
{
case WAIT_OBJECT_0:
- res = _my_tls.infodata.si_signo;
- sigproc_printf ("returning sig %d", res);
- if (info)
- *info = _my_tls.infodata;
+ if (!sigismember (set, _my_tls.infodata.si_signo))
+ {
+ set_errno (EINTR);
+ res = -1;
+ }
+ else
+ {
+ if (info)
+ *info = _my_tls.infodata;
+ res = _my_tls.infodata.si_signo;
+ InterlockedExchange ((LONG *) &_my_tls.sig, (LONG) 0);
+ }
break;
default:
__seterrno ();
res = -1;
}
- _my_tls.event = NULL;
- InterlockedExchange ((LONG *) &_my_tls.sig, (LONG) 0);
CloseHandle (h);
- sig_dispatch_pending ();
+ sigproc_printf ("returning sig %d", res);
return res;
}
+
+extern "C" int
+sigqueue (pid_t pid, int sig, const union sigval value)
+{
+ siginfo_t si;
+ pinfo dest (pid);
+ if (!dest)
+ {
+ set_errno (ESRCH);
+ return -1;
+ }
+ si.si_signo = sig;
+ si.si_code = SI_USER;
+ si.si_pid = si.si_uid = si.si_errno = 0;
+ si.si_value = value;
+ return sig_send (dest, si);
+}