Edit report at https://bugs.php.net/bug.php?id=47918&edit=1
ID: 47918
Comment by: webmaster_20161108 at cubiclesoft dot com
Reported by: RQuadling at GMail dot com
Summary: stream_set_blocking() does not work with pipes
opened with proc_open()
Status: Wont fix
Type: Bug
Package: Streams related
Operating System: Windows
PHP Version: 5.*, 6CVS (2009-06-19
Block user comment: N
Private report: N
New Comment:
There is now a workaround for this issue on Windows for all versions of PHP (and other scripting
languages with similar problems).
https://github.com/cubiclesoft/createprocess-windows
Before calling proc_open(), start a TCP/IP server in your PHP userland code. Then pass the IP
address and port number to 'createprocess.exe' using the /socketip and /socketport options
and use the /w /stdin=socket /stdout=socket /stderr=socket options as well. Three TCP/IP
connections will be established from 'createprocess.exe' and the first byte of data on
each stream indicates the file descriptor associated with the stream (0x00 = stdin, 0x01 = stdout,
0x02 = stderr). The sockets are passed to the final process via the standard handles that
'createprocess.exe' then runs. The /w option waits for the target process to complete
before closing the TCP/IP sockets and exiting.
After each TCP/IP connection has been established and the first byte of data has been received, you
can enable non-blocking mode and then proceed as if they were normal, non-blocking pipes on other
OSes.
Read the following StackOverflow post if you want to learn more about how this works/is possible:
http://stackoverflow.com/questions/4993119/redirect-io-of-process-to-windows-socket
Tip: Use "tcp://127.0.0.1:0" in the call to stream_socket_server() to get a random port
number assigned to the listening socket (the :0 part) and basically guarantee that the call
won't fail. Then use stream_socket_get_name($fp, false) to retrieve the 'IP:port'
associated with the socket to retrieve the port number that was assigned by the OS.
Previous Comments:
------------------------------------------------------------------------
[2014-09-29 14:49:26] ab@php.net
Related To: Bug #44908
------------------------------------------------------------------------
[2014-09-29 14:49:01] ab@php.net
Related To: Bug #63922
------------------------------------------------------------------------
[2014-09-29 14:47:49] ab@php.net
I have to disappoint here, the anonymous pipes are plain file descriptors, they don't support
asynchronous mode on Windows. The following page sheds more light on this:
http://msdn.microsoft.com/en-us/library/windows/desktop/aa365141%28v=vs.85%29.aspx
Because of them being file descriptors, they're also not supported by select() which requires
SOCKETS.
Please take in account the solution brought by bug #51800 . Pipe descriptors MUST be read
simultaneously. In this regard, bug #63922 and bug #44908 can be closed as well as they regard to
the Windows APIs behaviors which cannot be changed.
Thanks.
------------------------------------------------------------------------
[2014-06-06 20:26:06] cxjohnson at gmail dot com
Or more precisely, stream_get_meta_data() is broken. It reports the mode as blocked, yet a read on
the pipe while after stream_set_blocking($pipe, 0) does NOT block, as would be expected.
------------------------------------------------------------------------
[2014-06-06 20:15:53] cxjohnson at gmail dot com
Still broken in 5.4+.
This fails in the same way on Mac OSX 10.9.3 with PHP 5.4.24, and on FreeBSD 9.2-RELEASE with PHP
5.4.25.
------------------------------------------------------------------------
The remainder of the comments for this report are too long. To view
the rest of the comments, please view the bug report online at
https://bugs.php.net/bug.php?id=47918
--
Edit this bug report at https://bugs.php.net/bug.php?id=47918&edit=1