Schannel: Return if socket is invalid

In a couple places we already check if the socket is connected,
however we can be connected _and_ have the socket be closed.
The logic behind that I don't really understand, but there are
similar checks for validity in the OpenSSL backend.

This happens when calling close() on a still-connecting
socket. The QIODevice is marked as closed, but the connection
cannot yet be aborted. And when it finishes connecting we
handle the signal, start encryption, and then disconnect.

Pick-to: 6.6 6.5
Fixes: QTBUG-116550
Change-Id: I06c0a2db32bea0b573a99a971b8fb0b66a7a73d5
Reviewed-by: Edward Welbourne <edward.welbourne@qt.io>
bb10
Mårten Nordheim 2023-10-20 17:54:02 +02:00
parent c31227a548
commit 3ea46fa978
1 changed files with 4 additions and 2 deletions

View File

@ -1023,6 +1023,8 @@ bool TlsCryptographSchannel::sendToken(void *token, unsigned long tokenLength, b
Q_ASSERT(d);
auto *plainSocket = d->plainTcpSocket();
Q_ASSERT(plainSocket);
if (plainSocket->state() == QAbstractSocket::UnconnectedState || !plainSocket->isValid())
return false;
const qint64 written = plainSocket->write(static_cast<const char *>(token), tokenLength);
if (written != qint64(tokenLength)) {
@ -1385,7 +1387,7 @@ bool TlsCryptographSchannel::performHandshake()
auto *plainSocket = d->plainTcpSocket();
Q_ASSERT(plainSocket);
if (plainSocket->state() == QAbstractSocket::UnconnectedState) {
if (plainSocket->state() == QAbstractSocket::UnconnectedState || !plainSocket->isValid()) {
setErrorAndEmit(d, QAbstractSocket::RemoteHostClosedError,
QSslSocket::tr("The TLS/SSL connection has been closed"));
return false;
@ -1761,7 +1763,7 @@ void TlsCryptographSchannel::transmit()
return; // This function should not have been called
// Can happen if called through QSslSocket::abort->QSslSocket::close->QSslSocket::flush->here
if (plainSocket->state() == QAbstractSocket::SocketState::UnconnectedState)
if (plainSocket->state() == QAbstractSocket::UnconnectedState || !plainSocket->isValid())
return;
if (schannelState != SchannelState::Done) {