aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCorinna Vinschen <corinna@vinschen.de>2011-08-13 10:28:15 +0000
committerCorinna Vinschen <corinna@vinschen.de>2011-08-13 10:28:15 +0000
commitf8b8b1be3cbd92e934a173823d656f3e8363eb49 (patch)
tree69359ec12545c9c8339b148bbf00640432da93a1
parent41178da53306956423d8f04a446ca59cea2205eb (diff)
downloadnewlib-f8b8b1be3cbd92e934a173823d656f3e8363eb49.zip
newlib-f8b8b1be3cbd92e934a173823d656f3e8363eb49.tar.gz
newlib-f8b8b1be3cbd92e934a173823d656f3e8363eb49.tar.bz2
* miscfuncs.cc (CreatePipeOverlapped): New function.
(ReadPipeOverlapped): Ditto. (WritePipeOverlapped): Ditto. * miscfuncs.h: Declare new functions. * pinfo.cc (commune_process): Call WritePipeOverlapped instead of WriteFile. Set timeout to 1 sec. (_pinfo::commune_request): Call ReadPipeOverlapped instead of ReadFile. Set timeout to 0.5 secs. * sigproc.cc (sig_send): Create pipe using CreatePipeOverlapped.
-rw-r--r--winsup/cygwin/ChangeLog12
-rw-r--r--winsup/cygwin/miscfuncs.cc51
-rw-r--r--winsup/cygwin/miscfuncs.h7
-rw-r--r--winsup/cygwin/pinfo.cc60
-rw-r--r--winsup/cygwin/sigproc.cc2
5 files changed, 103 insertions, 29 deletions
diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog
index 759d0c8..67b8441 100644
--- a/winsup/cygwin/ChangeLog
+++ b/winsup/cygwin/ChangeLog
@@ -1,3 +1,15 @@
+2011-08-13 Corinna Vinschen <corinna@vinschen.de>
+
+ * miscfuncs.cc (CreatePipeOverlapped): New function.
+ (ReadPipeOverlapped): Ditto.
+ (WritePipeOverlapped): Ditto.
+ * miscfuncs.h: Declare new functions.
+ * pinfo.cc (commune_process): Call WritePipeOverlapped instead of
+ WriteFile. Set timeout to 1 sec.
+ (_pinfo::commune_request): Call ReadPipeOverlapped instead of ReadFile.
+ Set timeout to 0.5 secs.
+ * sigproc.cc (sig_send): Create pipe using CreatePipeOverlapped.
+
2011-08-12 Christopher Faylor <me.cygwin2011@cgf.cx>
* miscfuncs.cc (create_pipe): Delete obsolete function.
diff --git a/winsup/cygwin/miscfuncs.cc b/winsup/cygwin/miscfuncs.cc
index 42880c1..755a058 100644
--- a/winsup/cygwin/miscfuncs.cc
+++ b/winsup/cygwin/miscfuncs.cc
@@ -332,6 +332,57 @@ nice_to_winprio (int &nice)
return prio;
}
+/* Minimal overlapped pipe I/O implementation for signal and commune stuff. */
+
+BOOL WINAPI
+CreatePipeOverlapped (PHANDLE hr, PHANDLE hw, LPSECURITY_ATTRIBUTES sa)
+{
+ int ret = fhandler_pipe::create_selectable (sa, *hr, *hw, 0);
+ if (ret)
+ SetLastError (ret);
+ return ret == 0;
+}
+
+BOOL WINAPI
+ReadPipeOverlapped (HANDLE h, PVOID buf, DWORD len, LPDWORD ret_len,
+ DWORD timeout)
+{
+ OVERLAPPED ov;
+ BOOL ret;
+
+ memset (&ov, 0, sizeof ov);
+ ov.hEvent = CreateEvent (NULL, TRUE, FALSE, NULL);
+ ret = ReadFile (h, buf, len, NULL, &ov);
+ if (ret || GetLastError () == ERROR_IO_PENDING)
+ {
+ if (!ret && WaitForSingleObject (ov.hEvent, timeout) != WAIT_OBJECT_0)
+ CancelIo (h);
+ ret = GetOverlappedResult (h, &ov, ret_len, FALSE);
+ }
+ CloseHandle (ov.hEvent);
+ return ret;
+}
+
+BOOL WINAPI
+WritePipeOverlapped (HANDLE h, PCVOID buf, DWORD len, LPDWORD ret_len,
+ DWORD timeout)
+{
+ OVERLAPPED ov;
+ BOOL ret;
+
+ memset (&ov, 0, sizeof ov);
+ ov.hEvent = CreateEvent (NULL, TRUE, FALSE, NULL);
+ ret = WriteFile (h, buf, len, NULL, &ov);
+ if (ret || GetLastError () == ERROR_IO_PENDING)
+ {
+ if (!ret && WaitForSingleObject (ov.hEvent, timeout) != WAIT_OBJECT_0)
+ CancelIo (h);
+ ret = GetOverlappedResult (h, &ov, ret_len, FALSE);
+ }
+ CloseHandle (ov.hEvent);
+ return ret;
+}
+
/* backslashify: Convert all forward slashes in src path to back slashes
in dst path. Add a trailing slash to dst when trailing_slash_p arg
is set to 1. */
diff --git a/winsup/cygwin/miscfuncs.h b/winsup/cygwin/miscfuncs.h
index 0cff6c2..9ec6f59 100644
--- a/winsup/cygwin/miscfuncs.h
+++ b/winsup/cygwin/miscfuncs.h
@@ -17,6 +17,13 @@ DWORD nice_to_winprio (int &) __attribute__ ((regparm (1)));
bool __stdcall create_pipe (PHANDLE, PHANDLE, LPSECURITY_ATTRIBUTES, DWORD)
__attribute__ ((regparm (3)));
+BOOL WINAPI CreatePipeOverlapped (PHANDLE read_handle, PHANDLE write_handle,
+ LPSECURITY_ATTRIBUTES sa);
+BOOL WINAPI ReadPipeOverlapped (HANDLE h, PVOID buf, DWORD len,
+ LPDWORD ret_len, DWORD timeout);
+BOOL WINAPI WritePipeOverlapped (HANDLE h, PCVOID buf, DWORD len,
+ LPDWORD ret_len, DWORD timeout);
+
extern "C" void yield ();
void backslashify (const char *, char *, bool);
diff --git a/winsup/cygwin/pinfo.cc b/winsup/cygwin/pinfo.cc
index 89a96ef..4e63e23 100644
--- a/winsup/cygwin/pinfo.cc
+++ b/winsup/cygwin/pinfo.cc
@@ -483,16 +483,17 @@ commune_process (void *arg)
n += strlen (argv[i]) + 1;
}
argv[__argc_safe] = NULL;
- if (!WriteFile (tothem, &n, sizeof n, &nr, NULL))
+ if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
{
/*__seterrno ();*/ // this is run from the signal thread, so don't set errno
- sigproc_printf ("WriteFile sizeof argv failed, %E");
+ sigproc_printf ("WritePipeOverlapped sizeof argv failed, %E");
}
else
for (const char **a = argv; *a; a++)
- if (!WriteFile (tothem, *a, strlen (*a) + 1, &nr, NULL))
+ if (!WritePipeOverlapped (tothem, *a, strlen (*a) + 1, &nr, 1000L))
{
- sigproc_printf ("WriteFile arg %d failed, %E", a - argv);
+ sigproc_printf ("WritePipeOverlapped arg %d failed, %E",
+ a - argv);
break;
}
break;
@@ -501,10 +502,10 @@ commune_process (void *arg)
{
sigproc_printf ("processing PICOM_CWD");
unsigned int n = strlen (cygheap->cwd.get (path, 1, 1, NT_MAX_PATH)) + 1;
- if (!WriteFile (tothem, &n, sizeof n, &nr, NULL))
- sigproc_printf ("WriteFile sizeof cwd failed, %E");
- else if (!WriteFile (tothem, path, n, &nr, NULL))
- sigproc_printf ("WriteFile cwd failed, %E");
+ if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped sizeof cwd failed, %E");
+ else if (!WritePipeOverlapped (tothem, path, n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped cwd failed, %E");
break;
}
case PICOM_ROOT:
@@ -515,10 +516,10 @@ commune_process (void *arg)
n = strlen (strcpy (path, cygheap->root.posix_path ())) + 1;
else
n = strlen (strcpy (path, "/")) + 1;
- if (!WriteFile (tothem, &n, sizeof n, &nr, NULL))
- sigproc_printf ("WriteFile sizeof root failed, %E");
- else if (!WriteFile (tothem, path, n, &nr, NULL))
- sigproc_printf ("WriteFile root failed, %E");
+ if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped sizeof root failed, %E");
+ else if (!WritePipeOverlapped (tothem, path, n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped root failed, %E");
break;
}
case PICOM_FDS:
@@ -530,13 +531,13 @@ commune_process (void *arg)
while ((fd = cfd.next ()) >= 0)
n += sizeof (int);
cfd.rewind ();
- if (!WriteFile (tothem, &n, sizeof n, &nr, NULL))
- sigproc_printf ("WriteFile sizeof fds failed, %E");
+ if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped sizeof fds failed, %E");
else
while ((fd = cfd.next ()) >= 0)
- if (!WriteFile (tothem, &fd, sizeof fd, &nr, NULL))
+ if (!WritePipeOverlapped (tothem, &fd, sizeof fd, &nr, 1000L))
{
- sigproc_printf ("WriteFile fd %d failed, %E", fd);
+ sigproc_printf ("WritePipeOverlapped fd %d failed, %E", fd);
break;
}
break;
@@ -552,14 +553,14 @@ commune_process (void *arg)
{
fhandler_pipe *fh = cfd;
n = sizeof *fh;
- if (!WriteFile (tothem, &n, sizeof n, &nr, NULL))
- sigproc_printf ("WriteFile sizeof hdl failed, %E");
- else if (!WriteFile (tothem, fh, n, &nr, NULL))
- sigproc_printf ("WriteFile hdl failed, %E");
+ if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped sizeof hdl failed, %E");
+ else if (!WritePipeOverlapped (tothem, fh, n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped hdl failed, %E");
break;
}
- if (!n && !WriteFile (tothem, &n, sizeof n, &nr, NULL))
- sigproc_printf ("WriteFile sizeof hdl failed, %E");
+ if (!n && !WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped sizeof hdl failed, %E");
break;
}
case PICOM_FD:
@@ -572,10 +573,10 @@ commune_process (void *arg)
n = strlen (strcpy (path, "")) + 1;
else
n = strlen (cfd->get_proc_fd_name (path)) + 1;
- if (!WriteFile (tothem, &n, sizeof n, &nr, NULL))
- sigproc_printf ("WriteFile sizeof fd failed, %E");
- else if (!WriteFile (tothem, path, n, &nr, NULL))
- sigproc_printf ("WriteFile fd failed, %E");
+ if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped sizeof fd failed, %E");
+ else if (!WritePipeOverlapped (tothem, path, n, &nr, 1000L))
+ sigproc_printf ("WritePipeOverlapped fd failed, %E");
break;
}
}
@@ -655,7 +656,8 @@ _pinfo::commune_request (__uint32_t code, ...)
case PICOM_FDS:
case PICOM_FD:
case PICOM_PIPE_FHANDLER:
- if (!ReadFile (fromthem, &n, sizeof n, &nr, NULL) || nr != sizeof n)
+ if (!ReadPipeOverlapped (fromthem, &n, sizeof n, &nr, 500L)
+ || nr != sizeof n)
{
__seterrno ();
goto err;
@@ -666,7 +668,9 @@ _pinfo::commune_request (__uint32_t code, ...)
{
res.s = (char *) cmalloc_abort (HEAP_COMMUNE, n);
char *p;
- for (p = res.s; n && ReadFile (fromthem, p, n, &nr, NULL); p += nr, n -= nr)
+ for (p = res.s;
+ n && ReadPipeOverlapped (fromthem, p, n, &nr, 500L);
+ p += nr, n -= nr)
continue;
if (n)
{
diff --git a/winsup/cygwin/sigproc.cc b/winsup/cygwin/sigproc.cc
index db4c02f..26f50f7 100644
--- a/winsup/cygwin/sigproc.cc
+++ b/winsup/cygwin/sigproc.cc
@@ -608,7 +608,7 @@ sig_send (_pinfo *p, siginfo_t& si, _cygtls *tls)
HANDLE& tome = si._si_commune._si_write_handle;
HANDLE& fromthem = si._si_commune._si_read_handle;
- if (!CreatePipe (&fromthem, &tome, &sec_all_nih, 0))
+ if (!CreatePipeOverlapped (&fromthem, &tome, &sec_all_nih))
{
sigproc_printf ("CreatePipe for __SIGCOMMUNE failed, %E");
__seterrno ();