Bug #68853 [Asn]: stream_select on a TLS stream does not report last chunk as readable

From: Date: Sun, 08 Mar 2015 06:39:00 +0000
Subject: Bug #68853 [Asn]: stream_select on a TLS stream does not report last chunk as readable
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-191245@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=68853&edit=1 ID: 68853 Updated by: rdlowrey@php.net Reported by: boen dot robot at gmail dot com Summary: stream_select on a TLS stream does not report last chunk as readable Status: Assigned Type: Bug Package: OpenSSL related Operating System: Windows 2008 R2 PHP Version: 5.6.4 Assigned To: rdlowrey Block user comment: N Private report: N New Comment: Awesome. I may be able to hassle Ferenc to cherry-pick the fix into the 5.6.7 release even though it has already been tagged and branched. If not, it will be present in 5.6.8. I'll update this report with the version number once the question is resolved and I can close this issue. Thanks again for your *unending patience* with this bug. I've been working hard to address and close openssl issues. If you have future openssl-related problems they will hopefully be handled much quicker than this one was. Previous Comments: ------------------------------------------------------------------------ [2015-03-08 06:25:09] boen dot robot at gmail dot com I can confirm that the latest 5.6.8 snapshot fixes this issue. Thank you. ------------------------------------------------------------------------ [2015-03-06 17:35:40] rdlowrey@php.net Related To: Bug #65137 ------------------------------------------------------------------------ [2015-03-06 01:02:51] rdlowrey@php.net I have cherry-picked @DaveRandom's original SSL_pending() solution back into 5.6 and master. I'm fairly certain this commit solves the problem fully. It was unfortunately reverted due to its close proximity to some other buggy shenanigans. This change will *not* appear in the forthcoming 5.6.7 release so that we have time to test, get feedback and verify that it works everywhere. If you're interested in this bug's resolution please build the current PHP-5.6 or master branch to verify that the issue is resolved. ------------------------------------------------------------------------ [2015-01-18 15:35:12] boen dot robot at gmail dot com Description: ------------ If one end (say, client) sends more than one chunk of data (8192 bytes) at once, the last chunk (8192 or fewer remaining bytes) is not detected as readable by the other end (say, server) with stream_select() on the connection. Issue occurs on both ends if they do reading, so whether it's server receiving client data or client receiving server data - the same thing happens. This issue does not occur on a plain (non-encrypted) TCP stream. Only on encrypted streams. This is sort of related to #65137 in that it is apparently caused by stream_select() reporting the underlying TCP stream, rather than the TLS stream. By the time one calls stream_select() on the last chunk, the last chunk has already been read from the TCP layer, and is ready to be read, but there's no way to find that out from PHP userland. Not even stream_get_meta_data() helps - it reports 0 unread bytes after the last successful fread(). Test script: --------------- Here's an echo client/server duo demonstrating the issue. https://gist.github.com/boenrobot/f636eba79043f7303fb4 The server can be ran with the port as an argument, and an optional second argument with the protocol (tcp or tls; defaults to tcp). The client can be ran with the ip as a first argument, port as second, and optional port as third (again tcp or tls; defaults to tcp). From the client, you write the number of bytes to be sent to the server, with PHP_EOL appended after those, after which reading is done until PHP_EOL is found. (I also have an equivalent Java version, which I used to confirm that issue occurs on both client and server; You'll notice MakeKeys.php which generates a self signed certificate and exports it in .p12 format too - that was for the sake of Java) Expected result: ---------------- Same as with non-encrypted sockets - you write number of bytes, you send that many (plus EOL), and get that same many back (plus EOL), after which you can ask for more. Actual result: -------------- Trying to send f.e. 8191 on Windows (so 8193 bytes with the EOL in there) makes the server receive only 8192 bytes, and hanging on that last one. Same with any data larger than that, except that every next 8192 bytes are received, before the last chunk. ------------------------------------------------------------------------ -- Edit this bug report at https://bugs.php.net/bug.php?id=68853&edit=1

« previous php.bugs (#191245) next »