Details
-
Bug
-
Resolution: Done
-
P1: Critical
-
5.11.1, 5.12.3
-
None
-
3e939546e43ece26d0533fdd01f219e2993ae759 cea5603ee1a56bb5d177f35ed3f884345875099e
Description
In this QWebSocketServer's function:
void QWebSocketServerPrivate::handshakeReceived() { if (Q_UNLIKELY(!currentSender)) { return; } QTcpSocket *pTcpSocket = qobject_cast<QTcpSocket*>(currentSender->sender); if (Q_UNLIKELY(!pTcpSocket)) { return; } //When using Google Chrome the handshake in received in two parts. //Therefore, the readyRead signal is emitted twice. //This is a guard against the BEAST attack. //See: https://www.imperialviolet.org/2012/01/15/beastfollowup.html //For Safari, the handshake is delivered at once //FIXME: For FireFox, the readyRead signal is never emitted //This is a bug in FireFox (see https://bugzilla.mozilla.org/show_bug.cgi?id=594502) if (!pTcpSocket->canReadLine()) { return; }
The end of the HTTP Request Header is detected with
if (!pTcpSocket->canReadLine()) { return; }
{{}}This is incorrect, the marker for the end of the HTTP Header is "\r\n\r\n".
The current implementation could try to decode the http header when not received completely.
EDIT:
I have seen a proposed fix accepted for qt:
// According to RFC822 the body is separated from the headers by a null line (CRLF) if (!pTcpSocket->peek(pTcpSocket->bytesAvailable()).endsWith(QByteArrayLiteral("\r\n\r\n"))) { return; }
However this fix is still incorrect, it should with "contains()" instead of "endWith()". As the http request could have a content and not only a header. therefore the request will not end with "\r\n\r\n"
EDIT2:
It has not been fixed, please don't close it again