Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qsslsocket.cpp
Go to the documentation of this file.
1// Copyright (C) 2021 The Qt Company Ltd.
2// Copyright (C) 2014 BlackBerry Limited. All rights reserved.
3// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
4// Qt-Security score:significant reason:default
5
6
7//#define QSSLSOCKET_DEBUG
8
9/*!
10 \class QSslSocket
11 \brief The QSslSocket class provides an SSL encrypted socket for both
12 clients and servers.
13 \since 4.3
14
15 \reentrant
16 \ingroup network
17 \ingroup ssl
18 \inmodule QtNetwork
19
20 QSslSocket establishes a secure, encrypted TCP connection you can
21 use for transmitting encrypted data. It can operate in both client
22 and server mode, and it supports modern TLS protocols, including
23 TLS 1.3. By default, QSslSocket uses only TLS protocols
24 which are considered to be secure (QSsl::SecureProtocols), but you can
25 change the TLS protocol by calling setProtocol() as long as you do
26 it before the handshake has started.
27
28 SSL encryption operates on top of the existing TCP stream after
29 the socket enters the ConnectedState. There are two simple ways to
30 establish a secure connection using QSslSocket: With an immediate
31 SSL handshake, or with a delayed SSL handshake occurring after the
32 connection has been established in unencrypted mode.
33
34 The most common way to use QSslSocket is to construct an object
35 and start a secure connection by calling connectToHostEncrypted().
36 This method starts an immediate SSL handshake once the connection
37 has been established.
38
39 \snippet code/src_network_ssl_qsslsocket.cpp 0
40
41 As with a plain QTcpSocket, QSslSocket enters the HostLookupState,
42 ConnectingState, and finally the ConnectedState, if the connection
43 is successful. The handshake then starts automatically, and if it
44 succeeds, the encrypted() signal is emitted to indicate the socket
45 has entered the encrypted state and is ready for use.
46
47 Note that data can be written to the socket immediately after the
48 return from connectToHostEncrypted() (i.e., before the encrypted()
49 signal is emitted). The data is queued in QSslSocket until after
50 the encrypted() signal is emitted.
51
52 An example of using the delayed SSL handshake to secure an
53 existing connection is the case where an SSL server secures an
54 incoming connection. Suppose you create an SSL server class as a
55 subclass of QTcpServer. You would override
56 QTcpServer::incomingConnection() with something like the example
57 below, which first constructs an instance of QSslSocket and then
58 calls setSocketDescriptor() to set the new socket's descriptor to
59 the existing one passed in. It then initiates the SSL handshake
60 by calling startServerEncryption().
61
62 \snippet code/src_network_ssl_qsslsocket.cpp 1
63
64 If an error occurs, QSslSocket emits the sslErrors() signal. In this
65 case, if no action is taken to ignore the error(s), the connection
66 is dropped. To continue, despite the occurrence of an error, you
67 can call ignoreSslErrors(), either from within this slot after the
68 error occurs, or any time after construction of the QSslSocket and
69 before the connection is attempted. This will allow QSslSocket to
70 ignore the errors it encounters when establishing the identity of
71 the peer. Ignoring errors during an SSL handshake should be used
72 with caution, since a fundamental characteristic of secure
73 connections is that they should be established with a successful
74 handshake.
75
76 Once encrypted, you use QSslSocket as a regular QTcpSocket. When
77 readyRead() is emitted, you can call read(), canReadLine() and
78 readLine(), or getChar() to read decrypted data from QSslSocket's
79 internal buffer, and you can call write() or putChar() to write
80 data back to the peer. QSslSocket will automatically encrypt the
81 written data for you, and emit encryptedBytesWritten() once
82 the data has been written to the peer.
83
84 As a convenience, QSslSocket supports QTcpSocket's blocking
85 functions waitForConnected(), waitForReadyRead(),
86 waitForBytesWritten(), and waitForDisconnected(). It also provides
87 waitForEncrypted(), which will block the calling thread until an
88 encrypted connection has been established.
89
90 \snippet code/src_network_ssl_qsslsocket.cpp 2
91
92 QSslSocket provides an extensive, easy-to-use API for handling
93 cryptographic ciphers, private keys, and local, peer, and
94 Certification Authority (CA) certificates. It also provides an API
95 for handling errors that occur during the handshake phase.
96
97 The following features can also be customized:
98
99 \list
100 \li The socket's cryptographic cipher suite can be customized before
101 the handshake phase with QSslConfiguration::setCiphers().
102 \li The socket's local certificate and private key can be customized
103 before the handshake phase with setLocalCertificate() and
104 setPrivateKey().
105 \li The CA certificate database can be extended and customized with
106 QSslConfiguration::addCaCertificate(),
107 QSslConfiguration::addCaCertificates().
108 \endlist
109
110 To extend the list of \e default CA certificates used by the SSL sockets
111 during the SSL handshake you must update the default configuration, as
112 in the snippet below:
113
114 \code
115 QList<QSslCertificate> certificates = getCertificates();
116 QSslConfiguration configuration = QSslConfiguration::defaultConfiguration();
117 configuration.addCaCertificates(certificates);
118 QSslConfiguration::setDefaultConfiguration(configuration);
119 \endcode
120
121 \note If available, root certificates on Unix (excluding \macos) will be
122 loaded on demand from the standard certificate directories. If you do not
123 want to load root certificates on demand, you need to call either
124 QSslConfiguration::defaultConfiguration().setCaCertificates() before the first
125 SSL handshake is made in your application (for example, via passing
126 QSslSocket::systemCaCertificates() to it), or call
127 QSslConfiguration::defaultConfiguration()::setCaCertificates() on your QSslSocket instance
128 prior to the SSL handshake.
129
130 For more information about ciphers and certificates, refer to QSslCipher and
131 QSslCertificate.
132
133 This product includes software developed by the OpenSSL Project
134 for use in the OpenSSL Toolkit (\l{http://www.openssl.org/}).
135
136 \note Be aware of the difference between the bytesWritten() signal and
137 the encryptedBytesWritten() signal. For a QTcpSocket, bytesWritten()
138 will get emitted as soon as data has been written to the TCP socket.
139 For a QSslSocket, bytesWritten() will get emitted when the data
140 is being encrypted and encryptedBytesWritten()
141 will get emitted as soon as data has been written to the TCP socket.
142
143 \sa QSslCertificate, QSslCipher, QSslError
144*/
145
146/*!
147 \enum QSslSocket::SslMode
148
149 Describes the connection modes available for QSslSocket.
150
151 \value UnencryptedMode The socket is unencrypted. Its
152 behavior is identical to QTcpSocket.
153
154 \value SslClientMode The socket is a client-side SSL socket.
155 It is either already encrypted, or it is in the SSL handshake
156 phase (see QSslSocket::isEncrypted()).
157
158 \value SslServerMode The socket is a server-side SSL socket.
159 It is either already encrypted, or it is in the SSL handshake
160 phase (see QSslSocket::isEncrypted()).
161*/
162
163/*!
164 \enum QSslSocket::PeerVerifyMode
165 \since 4.4
166
167 Describes the peer verification modes for QSslSocket. The default mode is
168 AutoVerifyPeer, which selects an appropriate mode depending on the
169 socket's QSocket::SslMode.
170
171 \value VerifyNone QSslSocket will not request a certificate from the
172 peer. You can set this mode if you are not interested in the identity of
173 the other side of the connection. The connection will still be encrypted,
174 and your socket will still send its local certificate to the peer if it's
175 requested.
176
177 \value QueryPeer QSslSocket will request a certificate from the peer, but
178 does not require this certificate to be valid. This is useful when you
179 want to display peer certificate details to the user without affecting the
180 actual SSL handshake. This mode is the default for servers.
181 Note: In Schannel this value acts the same as VerifyNone.
182
183 \value VerifyPeer QSslSocket will request a certificate from the peer
184 during the SSL handshake phase, and requires that this certificate is
185 valid. On failure, QSslSocket will emit the QSslSocket::sslErrors()
186 signal. This mode is the default for clients.
187
188 \value AutoVerifyPeer QSslSocket will automatically use QueryPeer for
189 server sockets and VerifyPeer for client sockets.
190
191 \sa QSslSocket::peerVerifyMode()
192*/
193
194/*!
195 \fn void QSslSocket::encrypted()
196
197 This signal is emitted when QSslSocket enters encrypted mode. After this
198 signal has been emitted, QSslSocket::isEncrypted() will return true, and
199 all further transmissions on the socket will be encrypted.
200
201 \sa QSslSocket::connectToHostEncrypted(), QSslSocket::isEncrypted()
202*/
203
204/*!
205 \fn void QSslSocket::modeChanged(QSslSocket::SslMode mode)
206
207 This signal is emitted when QSslSocket changes from \l
208 QSslSocket::UnencryptedMode to either \l QSslSocket::SslClientMode or \l
209 QSslSocket::SslServerMode. \a mode is the new mode.
210
211 \sa QSslSocket::mode()
212*/
213
214/*!
215 \fn void QSslSocket::encryptedBytesWritten(qint64 written)
216 \since 4.4
217
218 This signal is emitted when QSslSocket writes its encrypted data to the
219 network. The \a written parameter contains the number of bytes that were
220 successfully written.
221
222 \sa QIODevice::bytesWritten()
223*/
224
225/*!
226 \fn void QSslSocket::peerVerifyError(const QSslError &error)
227 \since 4.4
228
229 QSslSocket can emit this signal several times during the SSL handshake,
230 before encryption has been established, to indicate that an error has
231 occurred while establishing the identity of the peer. The \a error is
232 usually an indication that QSslSocket is unable to securely identify the
233 peer.
234
235 This signal provides you with an early indication when something's wrong.
236 By connecting to this signal, you can manually choose to tear down the
237 connection from inside the connected slot before the handshake has
238 completed. If no action is taken, QSslSocket will proceed to emitting
239 QSslSocket::sslErrors().
240
241 \sa sslErrors()
242*/
243
244/*!
245 \fn void QSslSocket::sslErrors(const QList<QSslError> &errors);
246
247 QSslSocket emits this signal after the SSL handshake to indicate that one
248 or more errors have occurred while establishing the identity of the
249 peer. The errors are usually an indication that QSslSocket is unable to
250 securely identify the peer. Unless any action is taken, the connection
251 will be dropped after this signal has been emitted.
252
253 If you want to continue connecting despite the errors that have occurred,
254 you must call QSslSocket::ignoreSslErrors() from inside a slot connected to
255 this signal. If you need to access the error list at a later point, you
256 can call sslHandshakeErrors().
257
258 \a errors contains one or more errors that prevent QSslSocket from
259 verifying the identity of the peer.
260
261 \note You cannot use Qt::QueuedConnection when connecting to this signal,
262 or calling QSslSocket::ignoreSslErrors() will have no effect.
263
264 \sa peerVerifyError()
265*/
266
267/*!
268 \fn void QSslSocket::preSharedKeyAuthenticationRequired(QSslPreSharedKeyAuthenticator *authenticator)
269 \since 5.5
270
271 QSslSocket emits this signal when it negotiates a PSK ciphersuite, and
272 therefore a PSK authentication is then required.
273
274 When using PSK, the client must send to the server a valid identity and a
275 valid pre shared key, in order for the SSL handshake to continue.
276 Applications can provide this information in a slot connected to this
277 signal, by filling in the passed \a authenticator object according to their
278 needs.
279
280 \note Ignoring this signal, or failing to provide the required credentials,
281 will cause the handshake to fail, and therefore the connection to be aborted.
282
283 \note The \a authenticator object is owned by the socket and must not be
284 deleted by the application.
285
286 \sa QSslPreSharedKeyAuthenticator
287*/
288
289/*!
290 \fn void QSslSocket::alertSent(QSsl::AlertLevel level, QSsl::AlertType type, const QString &description)
291
292 QSslSocket emits this signal if an alert message was sent to a peer. \a level
293 describes if it was a warning or a fatal error. \a type gives the code
294 of the alert message. When a textual description of the alert message is
295 available, it is supplied in \a description.
296
297 \note This signal is mostly informational and can be used for debugging
298 purposes, normally it does not require any actions from the application.
299 \note Not all backends support this functionality.
300
301 \sa alertReceived(), QSsl::AlertLevel, QSsl::AlertType
302*/
303
304/*!
305 \fn void QSslSocket::alertReceived(QSsl::AlertLevel level, QSsl::AlertType type, const QString &description)
306
307 QSslSocket emits this signal if an alert message was received from a peer.
308 \a level tells if the alert was fatal or it was a warning. \a type is the
309 code explaining why the alert was sent. When a textual description of
310 the alert message is available, it is supplied in \a description.
311
312 \note The signal is mostly for informational and debugging purposes and does not
313 require any handling in the application. If the alert was fatal, underlying
314 backend will handle it and close the connection.
315 \note Not all backends support this functionality.
316
317 \sa alertSent(), QSsl::AlertLevel, QSsl::AlertType
318*/
319
320/*!
321 \fn void QSslSocket::handshakeInterruptedOnError(const QSslError &error)
322
323 QSslSocket emits this signal if a certificate verification error was
324 found and if early error reporting was enabled in QSslConfiguration.
325 An application is expected to inspect the \a error and decide if
326 it wants to continue the handshake, or abort it and send an alert message
327 to the peer. The signal-slot connection must be direct.
328
329 \sa continueInterruptedHandshake(), sslErrors(), QSslConfiguration::setHandshakeMustInterruptOnError()
330*/
331
332/*!
333 \fn void QSslSocket::newSessionTicketReceived()
334 \since 5.15
335
336 If TLS 1.3 protocol was negotiated during a handshake, QSslSocket
337 emits this signal after receiving NewSessionTicket message. Session
338 and session ticket's lifetime hint are updated in the socket's
339 configuration. The session can be used for session resumption (and
340 a shortened handshake) in future TLS connections.
341
342 \note This functionality enabled only with OpenSSL backend and requires
343 OpenSSL v 1.1.1 or above.
344
345 \sa QSslSocket::sslConfiguration(), QSslConfiguration::sessionTicket(), QSslConfiguration::sessionTicketLifeTimeHint()
346*/
347
348#include "qssl_p.h"
349#include "qsslsocket.h"
350#include "qsslcipher.h"
351#include "qocspresponse.h"
352#include "qtlsbackend_p.h"
354#include "qsslsocket_p.h"
355
356#include <QtCore/qdebug.h>
357#include <QtCore/qdir.h>
358#include <QtCore/qmutex.h>
359#include <QtCore/qurl.h>
360#include <QtCore/qelapsedtimer.h>
361#include <QtNetwork/qhostaddress.h>
362#include <QtNetwork/qhostinfo.h>
363
365
366using namespace Qt::StringLiterals;
367
368#ifdef Q_OS_VXWORKS
369constexpr auto isVxworks = true;
370#else
371constexpr auto isVxworks = false;
372#endif
373
392Q_GLOBAL_STATIC(QSslSocketGlobalData, globalData)
393
394/*!
395 Constructs a QSslSocket object. \a parent is passed to QObject's
396 constructor. The new socket's \l {QSslCipher} {cipher} suite is
397 set to the one returned by the static method defaultCiphers().
398*/
399QSslSocket::QSslSocket(QObject *parent)
400 : QTcpSocket(*new QSslSocketPrivate, parent)
401{
402 Q_D(QSslSocket);
403#ifdef QSSLSOCKET_DEBUG
404 qCDebug(lcSsl) << "QSslSocket::QSslSocket(" << parent << "), this =" << (void *)this;
405#endif
406 d->q_ptr = this;
407 d->init();
408}
409
410/*!
411 Destroys the QSslSocket.
412*/
413QSslSocket::~QSslSocket()
414{
415 Q_D(QSslSocket);
416#ifdef QSSLSOCKET_DEBUG
417 qCDebug(lcSsl) << "QSslSocket::~QSslSocket(), this =" << (void *)this;
418#endif
419 delete d->plainSocket;
420 d->plainSocket = nullptr;
421}
422
423/*!
424 \reimp
425
426 \since 5.0
427
428 Continues data transfer on the socket after it has been paused. If
429 "setPauseMode(QAbstractSocket::PauseOnSslErrors);" has been called on
430 this socket and a sslErrors() signal is received, calling this method
431 is necessary for the socket to continue.
432
433 \sa QAbstractSocket::pauseMode(), QAbstractSocket::setPauseMode()
434*/
435void QSslSocket::resume()
436{
437 Q_D(QSslSocket);
438 if (!d->paused)
439 return;
440 // continuing might emit signals, rather do this through the event loop
441 QMetaObject::invokeMethod(this, "_q_resumeImplementation", Qt::QueuedConnection);
442}
443
444/*!
445 Starts an encrypted connection to the device \a hostName on \a
446 port, using \a mode as the \l OpenMode. This is equivalent to
447 calling connectToHost() to establish the connection, followed by a
448 call to startClientEncryption(). The \a protocol parameter can be
449 used to specify which network protocol to use (eg. IPv4 or IPv6).
450
451 QSslSocket first enters the HostLookupState. Then, after entering
452 either the event loop or one of the waitFor...() functions, it
453 enters the ConnectingState, emits connected(), and then initiates
454 the SSL client handshake. At each state change, QSslSocket emits
455 signal stateChanged().
456
457 After initiating the SSL client handshake, if the identity of the
458 peer can't be established, signal sslErrors() is emitted. If you
459 want to ignore the errors and continue connecting, you must call
460 ignoreSslErrors(), either from inside a slot function connected to
461 the sslErrors() signal, or prior to entering encrypted mode. If
462 ignoreSslErrors() is not called, the connection is dropped, signal
463 disconnected() is emitted, and QSslSocket returns to the
464 UnconnectedState.
465
466 If the SSL handshake is successful, QSslSocket emits encrypted().
467
468 \snippet code/src_network_ssl_qsslsocket.cpp 3
469
470 \note The example above shows that text can be written to
471 the socket immediately after requesting the encrypted connection,
472 before the encrypted() signal has been emitted. In such cases, the
473 text is queued in the object and written to the socket \e after
474 the connection is established and the encrypted() signal has been
475 emitted.
476
477 The default for \a mode is \l ReadWrite.
478
479 If you want to create a QSslSocket on the server side of a connection, you
480 should instead call startServerEncryption() upon receiving the incoming
481 connection through QTcpServer.
482
483 \sa connectToHost(), startClientEncryption(), waitForConnected(), waitForEncrypted()
484*/
485void QSslSocket::connectToHostEncrypted(const QString &hostName, quint16 port, OpenMode mode, NetworkLayerProtocol protocol)
486{
487 Q_D(QSslSocket);
488 if (d->state == ConnectedState || d->state == ConnectingState) {
489 qCWarning(lcSsl,
490 "QSslSocket::connectToHostEncrypted() called when already connecting/connected");
491 return;
492 }
493
494 if (!supportsSsl()) {
495 qCWarning(lcSsl, "QSslSocket::connectToHostEncrypted: TLS initialization failed");
496 d->setErrorAndEmit(QAbstractSocket::SslInternalError, tr("TLS initialization failed"));
497 return;
498 }
499
500 if (!d->verifyProtocolSupported("QSslSocket::connectToHostEncrypted:"))
501 return;
502
503 d->init();
504 d->autoStartHandshake = true;
505 d->initialized = true;
506
507 // Note: When connecting to localhost, some platforms (e.g., HP-UX and some BSDs)
508 // establish the connection immediately (i.e., first attempt).
509 connectToHost(hostName, port, mode, protocol);
510}
511
512/*!
513 \since 4.6
514 \overload
515
516 In addition to the original behaviour of connectToHostEncrypted,
517 this overloaded method enables the usage of a different hostname
518 (\a sslPeerName) for the certificate validation instead of
519 the one used for the TCP connection (\a hostName).
520
521 \sa connectToHostEncrypted()
522*/
523void QSslSocket::connectToHostEncrypted(const QString &hostName, quint16 port,
524 const QString &sslPeerName, OpenMode mode,
525 NetworkLayerProtocol protocol)
526{
527 Q_D(QSslSocket);
528 if (d->state == ConnectedState || d->state == ConnectingState) {
529 qCWarning(lcSsl,
530 "QSslSocket::connectToHostEncrypted() called when already connecting/connected");
531 return;
532 }
533
534 if (!supportsSsl()) {
535 qCWarning(lcSsl, "QSslSocket::connectToHostEncrypted: TLS initialization failed");
536 d->setErrorAndEmit(QAbstractSocket::SslInternalError, tr("TLS initialization failed"));
537 return;
538 }
539
540 d->init();
541 d->autoStartHandshake = true;
542 d->initialized = true;
543 d->verificationPeerName = sslPeerName;
544
545 // Note: When connecting to localhost, some platforms (e.g., HP-UX and some BSDs)
546 // establish the connection immediately (i.e., first attempt).
547 connectToHost(hostName, port, mode, protocol);
548}
549
550/*!
551 Initializes QSslSocket with the native socket descriptor \a
552 socketDescriptor. Returns \c true if \a socketDescriptor is accepted
553 as a valid socket descriptor; otherwise returns \c false.
554 The socket is opened in the mode specified by \a openMode, and
555 enters the socket state specified by \a state.
556
557 \note It is not possible to initialize two sockets with the same
558 native socket descriptor.
559
560 \sa socketDescriptor()
561*/
562bool QSslSocket::setSocketDescriptor(qintptr socketDescriptor, SocketState state, OpenMode openMode)
563{
564 Q_D(QSslSocket);
565#ifdef QSSLSOCKET_DEBUG
566 qCDebug(lcSsl) << "QSslSocket::setSocketDescriptor(" << socketDescriptor << ','
567 << state << ',' << openMode << ')';
568#endif
569 if (!d->plainSocket)
570 d->createPlainSocket(openMode);
571 bool retVal = d->plainSocket->setSocketDescriptor(socketDescriptor, state, openMode);
572 d->cachedSocketDescriptor = d->plainSocket->socketDescriptor();
573 d->setError(d->plainSocket->error(), d->plainSocket->errorString());
574 setSocketState(state);
575 setOpenMode(openMode);
576 setLocalPort(d->plainSocket->localPort());
577 setLocalAddress(d->plainSocket->localAddress());
578 setPeerPort(d->plainSocket->peerPort());
579 setPeerAddress(d->plainSocket->peerAddress());
580 setPeerName(d->plainSocket->peerName());
581 d->readChannelCount = d->plainSocket->readChannelCount();
582 d->writeChannelCount = d->plainSocket->writeChannelCount();
583 return retVal;
584}
585
586/*!
587 \since 4.6
588 Sets the given \a option to the value described by \a value.
589
590 \sa socketOption()
591*/
592void QSslSocket::setSocketOption(QAbstractSocket::SocketOption option, const QVariant &value)
593{
594 Q_D(QSslSocket);
595 if (d->plainSocket)
596 d->plainSocket->setSocketOption(option, value);
597}
598
599/*!
600 \since 4.6
601 Returns the value of the \a option option.
602
603 \sa setSocketOption()
604*/
605QVariant QSslSocket::socketOption(QAbstractSocket::SocketOption option)
606{
607 Q_D(QSslSocket);
608 if (d->plainSocket)
609 return d->plainSocket->socketOption(option);
610 else
611 return QVariant();
612}
613
614/*!
615 Returns the current mode for the socket; either UnencryptedMode, where
616 QSslSocket behaves identially to QTcpSocket, or one of SslClientMode or
617 SslServerMode, where the client is either negotiating or in encrypted
618 mode.
619
620 When the mode changes, QSslSocket emits modeChanged()
621
622 \sa SslMode
623*/
624QSslSocket::SslMode QSslSocket::mode() const
625{
626 Q_D(const QSslSocket);
627 return d->mode;
628}
629
630/*!
631 Returns \c true if the socket is encrypted; otherwise, false is returned.
632
633 An encrypted socket encrypts all data that is written by calling write()
634 or putChar() before the data is written to the network, and decrypts all
635 incoming data as the data is received from the network, before you call
636 read(), readLine() or getChar().
637
638 QSslSocket emits encrypted() when it enters encrypted mode.
639
640 You can call sessionCipher() to find which cryptographic cipher is used to
641 encrypt and decrypt your data.
642
643 \sa mode()
644*/
645bool QSslSocket::isEncrypted() const
646{
647 Q_D(const QSslSocket);
648 return d->connectionEncrypted;
649}
650
651/*!
652 Returns the socket's SSL protocol. By default, \l QSsl::SecureProtocols is used.
653
654 \sa setProtocol()
655*/
656QSsl::SslProtocol QSslSocket::protocol() const
657{
658 Q_D(const QSslSocket);
659 return d->configuration.protocol;
660}
661
662/*!
663 Sets the socket's SSL protocol to \a protocol. This will affect the next
664 initiated handshake; calling this function on an already-encrypted socket
665 will not affect the socket's protocol.
666*/
667void QSslSocket::setProtocol(QSsl::SslProtocol protocol)
668{
669 Q_D(QSslSocket);
670 d->configuration.protocol = protocol;
671}
672
673/*!
674 \since 4.4
675
676 Returns the socket's verify mode. This mode decides whether
677 QSslSocket should request a certificate from the peer (i.e., the client
678 requests a certificate from the server, or a server requesting a
679 certificate from the client), and whether it should require that this
680 certificate is valid.
681
682 The default mode is AutoVerifyPeer, which tells QSslSocket to use
683 VerifyPeer for clients and QueryPeer for servers.
684
685 \sa setPeerVerifyMode(), peerVerifyDepth(), mode()
686*/
687QSslSocket::PeerVerifyMode QSslSocket::peerVerifyMode() const
688{
689 Q_D(const QSslSocket);
690 return d->configuration.peerVerifyMode;
691}
692
693/*!
694 \since 4.4
695
696 Sets the socket's verify mode to \a mode. This mode decides whether
697 QSslSocket should request a certificate from the peer (i.e., the client
698 requests a certificate from the server, or a server requesting a
699 certificate from the client), and whether it should require that this
700 certificate is valid.
701
702 The default mode is AutoVerifyPeer, which tells QSslSocket to use
703 VerifyPeer for clients and QueryPeer for servers.
704
705 Setting this mode after encryption has started has no effect on the
706 current connection.
707
708 \sa peerVerifyMode(), setPeerVerifyDepth(), mode()
709*/
710void QSslSocket::setPeerVerifyMode(QSslSocket::PeerVerifyMode mode)
711{
712 Q_D(QSslSocket);
713 d->configuration.peerVerifyMode = mode;
714}
715
716/*!
717 \since 4.4
718
719 Returns the maximum number of certificates in the peer's certificate chain
720 to be checked during the SSL handshake phase, or 0 (the default) if no
721 maximum depth has been set, indicating that the whole certificate chain
722 should be checked.
723
724 The certificates are checked in issuing order, starting with the peer's
725 own certificate, then its issuer's certificate, and so on.
726
727 \sa setPeerVerifyDepth(), peerVerifyMode()
728*/
729int QSslSocket::peerVerifyDepth() const
730{
731 Q_D(const QSslSocket);
732 return d->configuration.peerVerifyDepth;
733}
734
735/*!
736 \since 4.4
737
738 Sets the maximum number of certificates in the peer's certificate chain to
739 be checked during the SSL handshake phase, to \a depth. Setting a depth of
740 0 means that no maximum depth is set, indicating that the whole
741 certificate chain should be checked.
742
743 The certificates are checked in issuing order, starting with the peer's
744 own certificate, then its issuer's certificate, and so on.
745
746 \sa peerVerifyDepth(), setPeerVerifyMode()
747*/
748void QSslSocket::setPeerVerifyDepth(int depth)
749{
750 Q_D(QSslSocket);
751 if (depth < 0) {
752 qCWarning(lcSsl, "QSslSocket::setPeerVerifyDepth: cannot set negative depth of %d", depth);
753 return;
754 }
755 d->configuration.peerVerifyDepth = depth;
756}
757
758/*!
759 \since 4.8
760
761 Returns the different hostname for the certificate validation, as set by
762 setPeerVerifyName or by connectToHostEncrypted.
763
764 \sa setPeerVerifyName(), connectToHostEncrypted()
765*/
766QString QSslSocket::peerVerifyName() const
767{
768 Q_D(const QSslSocket);
769 return d->verificationPeerName;
770}
771
772/*!
773 \since 4.8
774
775 Sets a different host name, given by \a hostName, for the certificate
776 validation instead of the one used for the TCP connection.
777
778 \sa connectToHostEncrypted()
779*/
780void QSslSocket::setPeerVerifyName(const QString &hostName)
781{
782 Q_D(QSslSocket);
783 d->verificationPeerName = hostName;
784}
785
786/*!
787 \reimp
788
789 Returns the number of decrypted bytes that are immediately available for
790 reading.
791*/
792qint64 QSslSocket::bytesAvailable() const
793{
794 Q_D(const QSslSocket);
795 if (d->mode == UnencryptedMode)
796 return QAbstractSocket::bytesAvailable() + (d->plainSocket ? d->plainSocket->bytesAvailable() : 0);
797 return QAbstractSocket::bytesAvailable();
798}
799
800/*!
801 \reimp
802
803 Returns the number of unencrypted bytes that are waiting to be encrypted
804 and written to the network.
805*/
806qint64 QSslSocket::bytesToWrite() const
807{
808 Q_D(const QSslSocket);
809 if (d->mode == UnencryptedMode)
810 return d->plainSocket ? d->plainSocket->bytesToWrite() : 0;
811 return d->writeBuffer.size();
812}
813
814/*!
815 \since 4.4
816
817 Returns the number of encrypted bytes that are awaiting decryption.
818 Normally, this function will return 0 because QSslSocket decrypts its
819 incoming data as soon as it can.
820*/
821qint64 QSslSocket::encryptedBytesAvailable() const
822{
823 Q_D(const QSslSocket);
824 if (d->mode == UnencryptedMode)
825 return 0;
826 return d->plainSocket->bytesAvailable();
827}
828
829/*!
830 \since 4.4
831
832 Returns the number of encrypted bytes that are waiting to be written to
833 the network.
834*/
835qint64 QSslSocket::encryptedBytesToWrite() const
836{
837 Q_D(const QSslSocket);
838 if (d->mode == UnencryptedMode)
839 return 0;
840 return d->plainSocket->bytesToWrite();
841}
842
843/*!
844 \reimp
845
846 Returns \c true if you can read one while line (terminated by a single ASCII
847 '\\n' character) of decrypted characters; otherwise, false is returned.
848*/
849bool QSslSocket::canReadLine() const
850{
851 Q_D(const QSslSocket);
852 if (d->mode == UnencryptedMode)
853 return QAbstractSocket::canReadLine() || (d->plainSocket && d->plainSocket->canReadLine());
854 return QAbstractSocket::canReadLine();
855}
856
857/*!
858 \reimp
859*/
860void QSslSocket::close()
861{
862#ifdef QSSLSOCKET_DEBUG
863 qCDebug(lcSsl) << "QSslSocket::close()";
864#endif
865 Q_D(QSslSocket);
866
867 // On Windows, CertGetCertificateChain is probably still doing its
868 // job, if the socket is re-used, we want to ignore its reported
869 // root CA.
870 if (auto *backend = d->backend.get())
871 backend->cancelCAFetch();
872
873 if (!d->abortCalled && (encryptedBytesToWrite() || !d->writeBuffer.isEmpty()))
874 flush();
875 if (d->plainSocket) {
876 if (d->abortCalled)
877 d->plainSocket->abort();
878 else
879 d->plainSocket->close();
880 }
881 QTcpSocket::close();
882
883 // must be cleared, reading/writing not possible on closed socket:
884 d->buffer.clear();
885 d->writeBuffer.clear();
886}
887
888/*!
889 \reimp
890*/
891bool QSslSocket::atEnd() const
892{
893 Q_D(const QSslSocket);
894 if (d->mode == UnencryptedMode)
895 return QAbstractSocket::atEnd() && (!d->plainSocket || d->plainSocket->atEnd());
896 return QAbstractSocket::atEnd();
897}
898
899/*!
900 \since 4.4
901
902 Sets the size of QSslSocket's internal read buffer to be \a size bytes.
903*/
904void QSslSocket::setReadBufferSize(qint64 size)
905{
906 Q_D(QSslSocket);
907 d->readBufferMaxSize = size;
908
909 if (d->plainSocket)
910 d->plainSocket->setReadBufferSize(size);
911}
912
913/*!
914 \since 4.4
915
916 Returns the socket's SSL configuration state. The default SSL
917 configuration of a socket is to use the default ciphers,
918 default CA certificates, no local private key or certificate.
919
920 The SSL configuration also contains fields that can change with
921 time without notice.
922
923 \sa localCertificate(), peerCertificate(), peerCertificateChain(),
924 sessionCipher(), privateKey(), QSslConfiguration::ciphers(),
925 QSslConfiguration::caCertificates()
926*/
927QSslConfiguration QSslSocket::sslConfiguration() const
928{
929 Q_D(const QSslSocket);
930
931 // create a deep copy of our configuration
932 QSslConfigurationPrivate *copy = new QSslConfigurationPrivate(d->configuration);
933 copy->ref.storeRelaxed(0); // the QSslConfiguration constructor refs up
934 copy->sessionCipher = d->sessionCipher();
935 copy->sessionProtocol = d->sessionProtocol();
936
937 return QSslConfiguration(copy);
938}
939
940/*!
941 \since 4.4
942
943 Sets the socket's SSL configuration to be the contents of \a configuration.
944 This function sets the local certificate, the ciphers, the private key and the CA
945 certificates to those stored in \a configuration.
946
947 It is not possible to set the SSL-state related fields.
948
949 \sa setLocalCertificate(), setPrivateKey(), QSslConfiguration::setCaCertificates(),
950 QSslConfiguration::setCiphers()
951*/
952void QSslSocket::setSslConfiguration(const QSslConfiguration &configuration)
953{
954 Q_D(QSslSocket);
955 d->configuration.localCertificateChain = configuration.localCertificateChain();
956 d->configuration.privateKey = configuration.privateKey();
957 d->configuration.ciphers = configuration.ciphers();
958 d->configuration.ellipticCurves = configuration.ellipticCurves();
959 d->configuration.preSharedKeyIdentityHint = configuration.preSharedKeyIdentityHint();
960 d->configuration.dhParams = configuration.diffieHellmanParameters();
961 d->configuration.caCertificates = configuration.caCertificates();
962 d->configuration.peerVerifyDepth = configuration.peerVerifyDepth();
963 d->configuration.peerVerifyMode = configuration.peerVerifyMode();
964 d->configuration.protocol = configuration.protocol();
965 d->configuration.backendConfig = configuration.backendConfiguration();
966 d->configuration.sslOptions = configuration.d->sslOptions;
967 d->configuration.sslSession = configuration.sessionTicket();
968 d->configuration.sslSessionTicketLifeTimeHint = configuration.sessionTicketLifeTimeHint();
969 d->configuration.nextAllowedProtocols = configuration.allowedNextProtocols();
970 d->configuration.nextNegotiatedProtocol = configuration.nextNegotiatedProtocol();
971 d->configuration.nextProtocolNegotiationStatus = configuration.nextProtocolNegotiationStatus();
972#if QT_CONFIG(ocsp)
973 d->configuration.ocspStaplingEnabled = configuration.ocspStaplingEnabled();
974#endif
975#if QT_CONFIG(openssl)
976 d->configuration.reportFromCallback = configuration.handshakeMustInterruptOnError();
977 d->configuration.missingCertIsFatal = configuration.missingCertificateIsFatal();
978#endif // openssl
979 // if the CA certificates were set explicitly (either via
980 // QSslConfiguration::setCaCertificates() or QSslSocket::setCaCertificates(),
981 // we cannot load the certificates on demand
982 if (!configuration.d->allowRootCertOnDemandLoading) {
983 d->allowRootCertOnDemandLoading = false;
984 d->configuration.allowRootCertOnDemandLoading = false;
985 }
986}
987
988/*!
989 Sets the certificate chain to be presented to the peer during the
990 SSL handshake to be \a localChain.
991
992 \sa QSslConfiguration::setLocalCertificateChain()
993 \since 5.1
994 */
995void QSslSocket::setLocalCertificateChain(const QList<QSslCertificate> &localChain)
996{
997 Q_D(QSslSocket);
998 d->configuration.localCertificateChain = localChain;
999}
1000
1001/*!
1002 Returns the socket's local \l {QSslCertificate} {certificate} chain,
1003 or an empty list if no local certificates have been assigned.
1004
1005 \sa setLocalCertificateChain()
1006 \since 5.1
1007*/
1008QList<QSslCertificate> QSslSocket::localCertificateChain() const
1009{
1010 Q_D(const QSslSocket);
1011 return d->configuration.localCertificateChain;
1012}
1013
1014/*!
1015 Sets the socket's local certificate to \a certificate. The local
1016 certificate is necessary if you need to confirm your identity to the
1017 peer. It is used together with the private key; if you set the local
1018 certificate, you must also set the private key.
1019
1020 The local certificate and private key are always necessary for server
1021 sockets, but are also rarely used by client sockets if the server requires
1022 the client to authenticate.
1023
1024 \note Secure Transport SSL backend on macOS may update the default keychain
1025 (the default is probably your login keychain) by importing your local certificates
1026 and keys. This can also result in system dialogs showing up and asking for
1027 permission when your application is using these private keys. If such behavior
1028 is undesired, set the QT_SSL_USE_TEMPORARY_KEYCHAIN environment variable to a
1029 non-zero value; this will prompt QSslSocket to use its own temporary keychain.
1030
1031 \sa localCertificate(), setPrivateKey()
1032*/
1033void QSslSocket::setLocalCertificate(const QSslCertificate &certificate)
1034{
1035 Q_D(QSslSocket);
1036 d->configuration.localCertificateChain = QList<QSslCertificate>();
1037 d->configuration.localCertificateChain += certificate;
1038}
1039
1040/*!
1041 \overload
1042
1043 Sets the socket's local \l {QSslCertificate} {certificate} to the
1044 first one found in file \a path, which is parsed according to the
1045 specified \a format.
1046*/
1047void QSslSocket::setLocalCertificate(const QString &path,
1048 QSsl::EncodingFormat format)
1049{
1050 QFile file(path);
1051 if (file.open(QIODevice::ReadOnly | QIODevice::Text))
1052 setLocalCertificate(QSslCertificate(file.readAll(), format));
1053
1054}
1055
1056/*!
1057 Returns the socket's local \l {QSslCertificate} {certificate}, or
1058 an empty certificate if no local certificate has been assigned.
1059
1060 \sa setLocalCertificate(), privateKey()
1061*/
1062QSslCertificate QSslSocket::localCertificate() const
1063{
1064 Q_D(const QSslSocket);
1065 if (d->configuration.localCertificateChain.isEmpty())
1066 return QSslCertificate();
1067 return d->configuration.localCertificateChain[0];
1068}
1069
1070/*!
1071 Returns the peer's digital certificate (i.e., the immediate
1072 certificate of the host you are connected to), or a null
1073 certificate, if the peer has not assigned a certificate.
1074
1075 The peer certificate is checked automatically during the
1076 handshake phase, so this function is normally used to fetch
1077 the certificate for display or for connection diagnostic
1078 purposes. It contains information about the peer, including
1079 its host name, the certificate issuer, and the peer's public
1080 key.
1081
1082 Because the peer certificate is set during the handshake phase, it
1083 is safe to access the peer certificate from a slot connected to
1084 the sslErrors() signal or the encrypted() signal.
1085
1086 If a null certificate is returned, it can mean the SSL handshake
1087 failed, or it can mean the host you are connected to doesn't have
1088 a certificate, or it can mean there is no connection.
1089
1090 If you want to check the peer's complete chain of certificates,
1091 use peerCertificateChain() to get them all at once.
1092
1093 \sa peerCertificateChain()
1094*/
1095QSslCertificate QSslSocket::peerCertificate() const
1096{
1097 Q_D(const QSslSocket);
1098 return d->configuration.peerCertificate;
1099}
1100
1101/*!
1102 Returns the peer's chain of digital certificates, or an empty list
1103 of certificates.
1104
1105 Peer certificates are checked automatically during the handshake
1106 phase. This function is normally used to fetch certificates for
1107 display, or for performing connection diagnostics. Certificates
1108 contain information about the peer and the certificate issuers,
1109 including host name, issuer names, and issuer public keys.
1110
1111 The peer certificates are set in QSslSocket during the handshake
1112 phase, so it is safe to call this function from a slot connected
1113 to the sslErrors() signal or the encrypted() signal.
1114
1115 If an empty list is returned, it can mean the SSL handshake
1116 failed, or it can mean the host you are connected to doesn't have
1117 a certificate, or it can mean there is no connection.
1118
1119 If you want to get only the peer's immediate certificate, use
1120 peerCertificate().
1121
1122 \sa peerCertificate()
1123*/
1124QList<QSslCertificate> QSslSocket::peerCertificateChain() const
1125{
1126 Q_D(const QSslSocket);
1127 return d->configuration.peerCertificateChain;
1128}
1129
1130/*!
1131 Returns the socket's cryptographic \l {QSslCipher} {cipher}, or a
1132 null cipher if the connection isn't encrypted. The socket's cipher
1133 for the session is set during the handshake phase. The cipher is
1134 used to encrypt and decrypt data transmitted through the socket.
1135
1136 QSslSocket also provides functions for setting the ordered list of
1137 ciphers from which the handshake phase will eventually select the
1138 session cipher. This ordered list must be in place before the
1139 handshake phase begins.
1140
1141 \sa QSslConfiguration::ciphers(), QSslConfiguration::setCiphers(),
1142 QSslConfiguration::setCiphers(),
1143 QSslConfiguration::ciphers(),
1144 QSslConfiguration::supportedCiphers()
1145*/
1146QSslCipher QSslSocket::sessionCipher() const
1147{
1148 Q_D(const QSslSocket);
1149 return d->sessionCipher();
1150}
1151
1152/*!
1153 Returns the socket's SSL/TLS protocol or UnknownProtocol if the
1154 connection isn't encrypted. The socket's protocol for the session
1155 is set during the handshake phase.
1156
1157 \sa protocol(), setProtocol()
1158 \since 5.4
1159*/
1160QSsl::SslProtocol QSslSocket::sessionProtocol() const
1161{
1162 Q_D(const QSslSocket);
1163 return d->sessionProtocol();
1164}
1165
1166/*!
1167 \since 5.13
1168
1169 This function returns Online Certificate Status Protocol responses that
1170 a server may send during a TLS handshake using OCSP stapling. The list
1171 is empty if no definitive response or no response at all was received.
1172
1173 \sa QSslConfiguration::setOcspStaplingEnabled()
1174*/
1175QList<QOcspResponse> QSslSocket::ocspResponses() const
1176{
1177 Q_D(const QSslSocket);
1178 if (const auto *backend = d->backend.get())
1179 return backend->ocsps();
1180 return {};
1181}
1182
1183/*!
1184 Sets the socket's private \l {QSslKey} {key} to \a key. The
1185 private key and the local \l {QSslCertificate} {certificate} are
1186 used by clients and servers that must prove their identity to
1187 SSL peers.
1188
1189 Both the key and the local certificate are required if you are
1190 creating an SSL server socket. If you are creating an SSL client
1191 socket, the key and local certificate are required if your client
1192 must identify itself to an SSL server.
1193
1194 \sa privateKey(), setLocalCertificate()
1195*/
1196void QSslSocket::setPrivateKey(const QSslKey &key)
1197{
1198 Q_D(QSslSocket);
1199 d->configuration.privateKey = key;
1200}
1201
1202/*!
1203 \overload
1204
1205 Reads the string in file \a fileName and decodes it using
1206 a specified \a algorithm and encoding \a format to construct
1207 an \l {QSslKey} {SSL key}. If the encoded key is encrypted,
1208 \a passPhrase is used to decrypt it.
1209
1210 The socket's private key is set to the constructed key. The
1211 private key and the local \l {QSslCertificate} {certificate} are
1212 used by clients and servers that must prove their identity to SSL
1213 peers.
1214
1215 Both the key and the local certificate are required if you are
1216 creating an SSL server socket. If you are creating an SSL client
1217 socket, the key and local certificate are required if your client
1218 must identify itself to an SSL server.
1219
1220 \sa privateKey(), setLocalCertificate()
1221*/
1222void QSslSocket::setPrivateKey(const QString &fileName, QSsl::KeyAlgorithm algorithm,
1223 QSsl::EncodingFormat format, const QByteArray &passPhrase)
1224{
1225 QFile file(fileName);
1226 if (!file.open(QIODevice::ReadOnly)) {
1227 qCWarning(lcSsl, "QSslSocket::setPrivateKey: Couldn't open file for reading");
1228 return;
1229 }
1230
1231 QSslKey key(file.readAll(), algorithm, format, QSsl::PrivateKey, passPhrase);
1232 if (key.isNull()) {
1233 qCWarning(lcSsl, "QSslSocket::setPrivateKey: "
1234 "The specified file does not contain a valid key");
1235 return;
1236 }
1237
1238 Q_D(QSslSocket);
1239 d->configuration.privateKey = key;
1240}
1241
1242/*!
1243 Returns this socket's private key.
1244
1245 \sa setPrivateKey(), localCertificate()
1246*/
1247QSslKey QSslSocket::privateKey() const
1248{
1249 Q_D(const QSslSocket);
1250 return d->configuration.privateKey;
1251}
1252
1253/*!
1254 Waits until the socket is connected, or \a msecs milliseconds,
1255 whichever happens first. If the connection has been established,
1256 this function returns \c true; otherwise it returns \c false.
1257
1258 \sa QAbstractSocket::waitForConnected()
1259*/
1260bool QSslSocket::waitForConnected(int msecs)
1261{
1262 Q_D(QSslSocket);
1263 if (!d->plainSocket)
1264 return false;
1265 bool retVal = d->plainSocket->waitForConnected(msecs);
1266 if (!retVal) {
1267 setSocketState(d->plainSocket->state());
1268 d->setError(d->plainSocket->error(), d->plainSocket->errorString());
1269 }
1270 return retVal;
1271}
1272
1273/*!
1274 Waits until the socket has completed the SSL handshake and has
1275 emitted encrypted(), or \a msecs milliseconds, whichever comes
1276 first. If encrypted() has been emitted, this function returns
1277 true; otherwise (e.g., the socket is disconnected, or the SSL
1278 handshake fails), false is returned.
1279
1280 The following example waits up to one second for the socket to be
1281 encrypted:
1282
1283 \snippet code/src_network_ssl_qsslsocket.cpp 5
1284
1285 If msecs is -1, this function will not time out.
1286
1287 \sa startClientEncryption(), startServerEncryption(), encrypted(), isEncrypted()
1288*/
1289bool QSslSocket::waitForEncrypted(int msecs)
1290{
1291 Q_D(QSslSocket);
1292 if (!d->plainSocket || d->connectionEncrypted)
1293 return false;
1294 if (d->mode == UnencryptedMode && !d->autoStartHandshake)
1295 return false;
1296 if (!d->verifyProtocolSupported("QSslSocket::waitForEncrypted:"))
1297 return false;
1298
1299 QElapsedTimer stopWatch;
1300 stopWatch.start();
1301
1302 if (d->plainSocket->state() != QAbstractSocket::ConnectedState) {
1303 // Wait until we've entered connected state.
1304 if (!d->plainSocket->waitForConnected(msecs))
1305 return false;
1306 }
1307
1308 while (!d->connectionEncrypted) {
1309 // Start the handshake, if this hasn't been started yet.
1310 if (d->mode == UnencryptedMode)
1311 startClientEncryption();
1312 // Loop, waiting until the connection has been encrypted or an error
1313 // occurs.
1314 if (!d->plainSocket->waitForReadyRead(qt_subtract_from_timeout(msecs, stopWatch.elapsed())))
1315 return false;
1316 }
1317 return d->connectionEncrypted;
1318}
1319
1320/*!
1321 \reimp
1322*/
1323bool QSslSocket::waitForReadyRead(int msecs)
1324{
1325 Q_D(QSslSocket);
1326 if (!d->plainSocket)
1327 return false;
1328 if (d->mode == UnencryptedMode && !d->autoStartHandshake)
1329 return d->plainSocket->waitForReadyRead(msecs);
1330
1331 // This function must return true if and only if readyRead() *was* emitted.
1332 // So we initialize "readyReadEmitted" to false and check if it was set to true.
1333 // waitForReadyRead() could be called recursively, so we can't use the same variable
1334 // (the inner waitForReadyRead() may fail, but the outer one still succeeded)
1335 bool readyReadEmitted = false;
1336 bool *previousReadyReadEmittedPointer = d->readyReadEmittedPointer;
1337 d->readyReadEmittedPointer = &readyReadEmitted;
1338
1339 QElapsedTimer stopWatch;
1340 stopWatch.start();
1341
1342 if (!d->connectionEncrypted) {
1343 // Wait until we've entered encrypted mode, or until a failure occurs.
1344 if (!waitForEncrypted(msecs)) {
1345 d->readyReadEmittedPointer = previousReadyReadEmittedPointer;
1346 return false;
1347 }
1348 }
1349
1350 if (!d->writeBuffer.isEmpty()) {
1351 // empty our cleartext write buffer first
1352 d->transmit();
1353 }
1354
1355 // test readyReadEmitted first because either operation above
1356 // (waitForEncrypted or transmit) may have set it
1357 while (!readyReadEmitted &&
1358 d->plainSocket->waitForReadyRead(qt_subtract_from_timeout(msecs, stopWatch.elapsed()))) {
1359 }
1360
1361 d->readyReadEmittedPointer = previousReadyReadEmittedPointer;
1362 return readyReadEmitted;
1363}
1364
1365/*!
1366 \reimp
1367*/
1368bool QSslSocket::waitForBytesWritten(int msecs)
1369{
1370 Q_D(QSslSocket);
1371 if (!d->plainSocket)
1372 return false;
1373 if (d->mode == UnencryptedMode)
1374 return d->plainSocket->waitForBytesWritten(msecs);
1375
1376 QElapsedTimer stopWatch;
1377 stopWatch.start();
1378
1379 if (!d->connectionEncrypted) {
1380 // Wait until we've entered encrypted mode, or until a failure occurs.
1381 if (!waitForEncrypted(msecs))
1382 return false;
1383 }
1384 if (!d->writeBuffer.isEmpty()) {
1385 // empty our cleartext write buffer first
1386 d->transmit();
1387 }
1388
1389 return d->plainSocket->waitForBytesWritten(qt_subtract_from_timeout(msecs, stopWatch.elapsed()));
1390}
1391
1392/*!
1393 Waits until the socket has disconnected or \a msecs milliseconds,
1394 whichever comes first. If the connection has been disconnected,
1395 this function returns \c true; otherwise it returns \c false.
1396
1397 \sa QAbstractSocket::waitForDisconnected()
1398*/
1399bool QSslSocket::waitForDisconnected(int msecs)
1400{
1401 Q_D(QSslSocket);
1402
1403 // require calling connectToHost() before waitForDisconnected()
1404 if (state() == UnconnectedState) {
1405 qCWarning(lcSsl, "QSslSocket::waitForDisconnected() is not allowed in UnconnectedState");
1406 return false;
1407 }
1408
1409 if (!d->plainSocket)
1410 return false;
1411 // Forward to the plain socket unless the connection is secure.
1412 if (d->mode == UnencryptedMode && !d->autoStartHandshake)
1413 return d->plainSocket->waitForDisconnected(msecs);
1414
1415 QElapsedTimer stopWatch;
1416 stopWatch.start();
1417
1418 if (!d->connectionEncrypted) {
1419 // Wait until we've entered encrypted mode, or until a failure occurs.
1420 if (!waitForEncrypted(msecs))
1421 return false;
1422 }
1423 // We are delaying the disconnect, if the write buffer is not empty.
1424 // So, start the transmission.
1425 if (!d->writeBuffer.isEmpty())
1426 d->transmit();
1427
1428 // At this point, the socket might be disconnected, if disconnectFromHost()
1429 // was called just after the connectToHostEncrypted() call. Also, we can
1430 // lose the connection as a result of the transmit() call.
1431 if (state() == UnconnectedState)
1432 return true;
1433
1434 bool retVal = d->plainSocket->waitForDisconnected(qt_subtract_from_timeout(msecs, stopWatch.elapsed()));
1435 if (!retVal) {
1436 setSocketState(d->plainSocket->state());
1437 d->setError(d->plainSocket->error(), d->plainSocket->errorString());
1438 }
1439 return retVal;
1440}
1441
1442/*!
1443 \since 5.15
1444
1445 Returns a list of the last SSL errors that occurred. This is the
1446 same list as QSslSocket passes via the sslErrors() signal. If the
1447 connection has been encrypted with no errors, this function will
1448 return an empty list.
1449
1450 \sa connectToHostEncrypted()
1451*/
1452QList<QSslError> QSslSocket::sslHandshakeErrors() const
1453{
1454 Q_D(const QSslSocket);
1455 if (const auto *backend = d->backend.get())
1456 return backend->tlsErrors();
1457 return {};
1458}
1459
1460/*!
1461 Returns \c true if this platform supports SSL; otherwise, returns
1462 false. If the platform doesn't support SSL, the socket will fail
1463 in the connection phase.
1464*/
1465bool QSslSocket::supportsSsl()
1466{
1467 return QSslSocketPrivate::supportsSsl();
1468}
1469
1470/*!
1471 \since 5.0
1472 Returns the version number of the SSL library in use. Note that
1473 this is the version of the library in use at run-time not compile
1474 time. If no SSL support is available then this will return -1.
1475*/
1476long QSslSocket::sslLibraryVersionNumber()
1477{
1478 if (const auto *tlsBackend = QSslSocketPrivate::tlsBackendInUse())
1479 return tlsBackend->tlsLibraryVersionNumber();
1480
1481 return -1;
1482}
1483
1484/*!
1485 \since 5.0
1486 Returns the version string of the SSL library in use. Note that
1487 this is the version of the library in use at run-time not compile
1488 time. If no SSL support is available then this will return an empty value.
1489*/
1490QString QSslSocket::sslLibraryVersionString()
1491{
1492 if (const auto *tlsBackend = QSslSocketPrivate::tlsBackendInUse())
1493 return tlsBackend->tlsLibraryVersionString();
1494 return {};
1495}
1496
1497/*!
1498 \since 5.4
1499 Returns the version number of the SSL library in use at compile
1500 time. If no SSL support is available then this will return -1.
1501
1502 \sa sslLibraryVersionNumber()
1503*/
1504long QSslSocket::sslLibraryBuildVersionNumber()
1505{
1506 if (const auto *tlsBackend = QSslSocketPrivate::tlsBackendInUse())
1507 return tlsBackend->tlsLibraryBuildVersionNumber();
1508 return -1;
1509}
1510
1511/*!
1512 \since 5.4
1513 Returns the version string of the SSL library in use at compile
1514 time. If no SSL support is available then this will return an
1515 empty value.
1516
1517 \sa sslLibraryVersionString()
1518*/
1519QString QSslSocket::sslLibraryBuildVersionString()
1520{
1521 if (const auto *tlsBackend = QSslSocketPrivate::tlsBackendInUse())
1522 return tlsBackend->tlsLibraryBuildVersionString();
1523
1524 return {};
1525}
1526
1527/*!
1528 \since 6.1
1529 Returns the names of the currently available backends. These names
1530 are in lower case, e.g. "openssl", "securetransport", "schannel"
1531 (similar to the already existing feature names for TLS backends in Qt).
1532
1533 \sa activeBackend()
1534*/
1535QList<QString> QSslSocket::availableBackends()
1536{
1537 return QTlsBackend::availableBackendNames();
1538}
1539
1540/*!
1541 \since 6.1
1542 Returns the name of the backend that QSslSocket and related classes
1543 use. If the active backend was not set explicitly, this function
1544 returns the name of a default backend that QSslSocket selects implicitly
1545 from the list of available backends.
1546
1547 \note When selecting a default backend implicitly, QSslSocket prefers
1548 the OpenSSL backend if available. If it's not available, the Schannel backend
1549 is implicitly selected on Windows, and Secure Transport on Darwin platforms.
1550 Failing these, if a custom TLS backend is found, it is used.
1551 If no other backend is found, the "certificate only" backend is selected.
1552 For more information about TLS plugins, please see
1553 \l {Enabling and Disabling SSL Support when Building Qt from Source}.
1554
1555 \sa setActiveBackend(), availableBackends()
1556*/
1557QString QSslSocket::activeBackend()
1558{
1559 const QMutexLocker locker(&QSslSocketPrivate::backendMutex);
1560
1561 if (!QSslSocketPrivate::activeBackendName.size())
1562 QSslSocketPrivate::activeBackendName = QTlsBackend::defaultBackendName();
1563
1564 return QSslSocketPrivate::activeBackendName;
1565}
1566
1567/*!
1568 \since 6.1
1569 Returns true if a backend with name \a backendName was set as
1570 active backend. \a backendName must be one of names returned
1571 by availableBackends().
1572
1573 \note An application cannot mix different backends simultaneously.
1574 This implies that a non-default backend must be selected prior
1575 to any use of QSslSocket or related classes, e.g. QSslCertificate
1576 or QSslKey.
1577
1578 \sa activeBackend(), availableBackends()
1579*/
1580bool QSslSocket::setActiveBackend(const QString &backendName)
1581{
1582 if (!backendName.size()) {
1583 qCWarning(lcSsl, "Invalid parameter (backend name cannot be an empty string)");
1584 return false;
1585 }
1586
1587 QMutexLocker locker(&QSslSocketPrivate::backendMutex);
1588 if (QSslSocketPrivate::tlsBackend) {
1589 qCWarning(lcSsl) << "Cannot set backend named" << backendName
1590 << "as active, another backend is already in use";
1591 locker.unlock();
1592 return activeBackend() == backendName;
1593 }
1594
1595 if (!QTlsBackend::availableBackendNames().contains(backendName)) {
1596 qCWarning(lcSsl) << "Cannot set unavailable backend named" << backendName
1597 << "as active";
1598 return false;
1599 }
1600
1601 QSslSocketPrivate::activeBackendName = backendName;
1602
1603 return true;
1604}
1605
1606/*!
1607 \since 6.1
1608 If a backend with name \a backendName is available, this function returns the
1609 list of TLS protocol versions supported by this backend. An empty \a backendName
1610 is understood as a query about the currently active backend. Otherwise, this
1611 function returns an empty list.
1612
1613 \sa availableBackends(), activeBackend(), isProtocolSupported()
1614*/
1615QList<QSsl::SslProtocol> QSslSocket::supportedProtocols(const QString &backendName)
1616{
1617 return QTlsBackend::supportedProtocols(backendName.size() ? backendName : activeBackend());
1618}
1619
1620/*!
1621 \since 6.1
1622 Returns true if \a protocol is supported by a backend named \a backendName. An empty
1623 \a backendName is understood as a query about the currently active backend.
1624
1625 \sa supportedProtocols()
1626*/
1627bool QSslSocket::isProtocolSupported(QSsl::SslProtocol protocol, const QString &backendName)
1628{
1629 const auto versions = supportedProtocols(backendName);
1630 return versions.contains(protocol);
1631}
1632
1633/*!
1634 \since 6.1
1635 This function returns backend-specific classes implemented by the backend named
1636 \a backendName. An empty \a backendName is understood as a query about the
1637 currently active backend.
1638
1639 \sa QSsl::ImplementedClass, activeBackend(), isClassImplemented()
1640*/
1641QList<QSsl::ImplementedClass> QSslSocket::implementedClasses(const QString &backendName)
1642{
1643 return QTlsBackend::implementedClasses(backendName.size() ? backendName : activeBackend());
1644}
1645
1646/*!
1647 \since 6.1
1648 Returns true if a class \a cl is implemented by the backend named \a backendName. An empty
1649 \a backendName is understood as a query about the currently active backend.
1650
1651 \sa implementedClasses()
1652*/
1653
1654bool QSslSocket::isClassImplemented(QSsl::ImplementedClass cl, const QString &backendName)
1655{
1656 return implementedClasses(backendName).contains(cl);
1657}
1658
1659/*!
1660 \since 6.1
1661 This function returns features supported by a backend named \a backendName.
1662 An empty \a backendName is understood as a query about the currently active backend.
1663
1664 \sa QSsl::SupportedFeature, activeBackend()
1665*/
1666QList<QSsl::SupportedFeature> QSslSocket::supportedFeatures(const QString &backendName)
1667{
1668 return QTlsBackend::supportedFeatures(backendName.size() ? backendName : activeBackend());
1669}
1670
1671/*!
1672 \since 6.1
1673 Returns true if a feature \a ft is supported by a backend named \a backendName. An empty
1674 \a backendName is understood as a query about the currently active backend.
1675
1676 \sa QSsl::SupportedFeature, supportedFeatures()
1677*/
1678bool QSslSocket::isFeatureSupported(QSsl::SupportedFeature ft, const QString &backendName)
1679{
1680 return supportedFeatures(backendName).contains(ft);
1681}
1682
1683/*!
1684 Starts a delayed SSL handshake for a client connection. This
1685 function can be called when the socket is in the \l ConnectedState
1686 but still in the \l UnencryptedMode. If it is not yet connected,
1687 or if it is already encrypted, this function has no effect.
1688
1689 Clients that implement STARTTLS functionality often make use of
1690 delayed SSL handshakes. Most other clients can avoid calling this
1691 function directly by using connectToHostEncrypted() instead, which
1692 automatically performs the handshake.
1693
1694 \sa connectToHostEncrypted(), startServerEncryption()
1695*/
1696void QSslSocket::startClientEncryption()
1697{
1698 Q_D(QSslSocket);
1699 if (d->mode != UnencryptedMode) {
1700 qCWarning(lcSsl,
1701 "QSslSocket::startClientEncryption: cannot start handshake on non-plain connection");
1702 return;
1703 }
1704 if (state() != ConnectedState) {
1705 qCWarning(lcSsl,
1706 "QSslSocket::startClientEncryption: cannot start handshake when not connected");
1707 return;
1708 }
1709
1710 if (!supportsSsl()) {
1711 qCWarning(lcSsl, "QSslSocket::startClientEncryption: TLS initialization failed");
1712 d->setErrorAndEmit(QAbstractSocket::SslInternalError, tr("TLS initialization failed"));
1713 return;
1714 }
1715
1716 if (!d->verifyProtocolSupported("QSslSocket::startClientEncryption:"))
1717 return;
1718
1719#ifdef QSSLSOCKET_DEBUG
1720 qCDebug(lcSsl) << "QSslSocket::startClientEncryption()";
1721#endif
1722 d->mode = SslClientMode;
1723 emit modeChanged(d->mode);
1724 d->startClientEncryption();
1725}
1726
1727/*!
1728 Starts a delayed SSL handshake for a server connection. This
1729 function can be called when the socket is in the \l ConnectedState
1730 but still in \l UnencryptedMode. If it is not connected or it is
1731 already encrypted, the function has no effect.
1732
1733 For server sockets, calling this function is the only way to
1734 initiate the SSL handshake. Most servers will call this function
1735 immediately upon receiving a connection, or as a result of having
1736 received a protocol-specific command to enter SSL mode (e.g, the
1737 server may respond to receiving the string "STARTTLS\\r\\n" by
1738 calling this function).
1739
1740 The most common way to implement an SSL server is to create a
1741 subclass of QTcpServer and reimplement
1742 QTcpServer::incomingConnection(). The returned socket descriptor
1743 is then passed to QSslSocket::setSocketDescriptor().
1744
1745 \sa connectToHostEncrypted(), startClientEncryption()
1746*/
1747void QSslSocket::startServerEncryption()
1748{
1749 Q_D(QSslSocket);
1750 if (d->mode != UnencryptedMode) {
1751 qCWarning(lcSsl, "QSslSocket::startServerEncryption: cannot start handshake on non-plain connection");
1752 return;
1753 }
1754#ifdef QSSLSOCKET_DEBUG
1755 qCDebug(lcSsl) << "QSslSocket::startServerEncryption()";
1756#endif
1757 if (!supportsSsl()) {
1758 qCWarning(lcSsl, "QSslSocket::startServerEncryption: TLS initialization failed");
1759 d->setErrorAndEmit(QAbstractSocket::SslInternalError, tr("TLS initialization failed"));
1760 return;
1761 }
1762 if (!d->verifyProtocolSupported("QSslSocket::startServerEncryption"))
1763 return;
1764
1765 d->mode = SslServerMode;
1766 emit modeChanged(d->mode);
1767 d->startServerEncryption();
1768}
1769
1770/*!
1771 This slot tells QSslSocket to ignore errors during QSslSocket's
1772 handshake phase and continue connecting. If you want to continue
1773 with the connection even if errors occur during the handshake
1774 phase, then you must call this slot, either from a slot connected
1775 to sslErrors(), or before the handshake phase. If you don't call
1776 this slot, either in response to errors or before the handshake,
1777 the connection will be dropped after the sslErrors() signal has
1778 been emitted.
1779
1780 If there are no errors during the SSL handshake phase (i.e., the
1781 identity of the peer is established with no problems), QSslSocket
1782 will not emit the sslErrors() signal, and it is unnecessary to
1783 call this function.
1784
1785 \warning Be sure to always let the user inspect the errors
1786 reported by the sslErrors() signal, and only call this method
1787 upon confirmation from the user that proceeding is ok.
1788 If there are unexpected errors, the connection should be aborted.
1789 Calling this method without inspecting the actual errors will
1790 most likely pose a security risk for your application. Use it
1791 with great care!
1792
1793 \sa sslErrors()
1794*/
1795void QSslSocket::ignoreSslErrors()
1796{
1797 Q_D(QSslSocket);
1798 d->ignoreAllSslErrors = true;
1799}
1800
1801/*!
1802 \overload
1803 \since 4.6
1804
1805 This method tells QSslSocket to ignore only the errors given in \a
1806 errors.
1807
1808 \note Because most SSL errors are associated with a certificate, for most
1809 of them you must set the expected certificate this SSL error is related to.
1810 If, for instance, you want to connect to a server that uses
1811 a self-signed certificate, consider the following snippet:
1812
1813 \snippet code/src_network_ssl_qsslsocket.cpp 6
1814
1815 Multiple calls to this function will replace the list of errors that
1816 were passed in previous calls.
1817 You can clear the list of errors you want to ignore by calling this
1818 function with an empty list.
1819
1820 \sa sslErrors(), sslHandshakeErrors()
1821*/
1822void QSslSocket::ignoreSslErrors(const QList<QSslError> &errors)
1823{
1824 Q_D(QSslSocket);
1825 d->ignoreErrorsList = errors;
1826}
1827
1828
1829/*!
1830 \since 6.0
1831
1832 If an application wants to conclude a handshake even after receiving
1833 handshakeInterruptedOnError() signal, it must call this function.
1834 This call must be done from a slot function attached to the signal.
1835 The signal-slot connection must be direct.
1836
1837 \sa handshakeInterruptedOnError(), QSslConfiguration::setHandshakeMustInterruptOnError()
1838*/
1839void QSslSocket::continueInterruptedHandshake()
1840{
1841 Q_D(QSslSocket);
1842 if (auto *backend = d->backend.get())
1843 backend->enableHandshakeContinuation();
1844}
1845
1846/*!
1847 \internal
1848*/
1849void QSslSocket::connectToHost(const QString &hostName, quint16 port, OpenMode openMode, NetworkLayerProtocol protocol)
1850{
1851 Q_D(QSslSocket);
1852 d->preferredNetworkLayerProtocol = protocol;
1853 if (!d->initialized)
1854 d->init();
1855 d->initialized = false;
1856
1857#ifdef QSSLSOCKET_DEBUG
1858 qCDebug(lcSsl) << "QSslSocket::connectToHost("
1859 << hostName << ',' << port << ',' << openMode << ')';
1860#endif
1861 if (!d->plainSocket) {
1862#ifdef QSSLSOCKET_DEBUG
1863 qCDebug(lcSsl) << "\tcreating internal plain socket";
1864#endif
1865 d->createPlainSocket(openMode);
1866 }
1867#ifndef QT_NO_NETWORKPROXY
1868 d->plainSocket->setProtocolTag(d->protocolTag);
1869 d->plainSocket->setProxy(proxy());
1870#endif
1871 QIODevice::open(openMode);
1872 d->readChannelCount = d->writeChannelCount = 0;
1873 d->plainSocket->connectToHost(hostName, port, openMode, d->preferredNetworkLayerProtocol);
1874 d->cachedSocketDescriptor = d->plainSocket->socketDescriptor();
1875}
1876
1877/*!
1878 \internal
1879*/
1880void QSslSocket::disconnectFromHost()
1881{
1882 Q_D(QSslSocket);
1883#ifdef QSSLSOCKET_DEBUG
1884 qCDebug(lcSsl) << "QSslSocket::disconnectFromHost()";
1885#endif
1886 if (!d->plainSocket)
1887 return;
1888 if (d->state == UnconnectedState)
1889 return;
1890 if (d->mode == UnencryptedMode && !d->autoStartHandshake) {
1891 d->plainSocket->disconnectFromHost();
1892 return;
1893 }
1894 if (d->state <= ConnectingState) {
1895 d->pendingClose = true;
1896 return;
1897 }
1898 // Make sure we don't process any signal from the CA fetcher
1899 // (Windows):
1900 if (auto *backend = d->backend.get())
1901 backend->cancelCAFetch();
1902
1903 // Perhaps emit closing()
1904 if (d->state != ClosingState) {
1905 d->state = ClosingState;
1906 emit stateChanged(d->state);
1907 }
1908
1909 if (!d->writeBuffer.isEmpty()) {
1910 d->pendingClose = true;
1911 return;
1912 }
1913
1914 if (d->mode == UnencryptedMode) {
1915 d->plainSocket->disconnectFromHost();
1916 } else {
1917 d->disconnectFromHost();
1918 }
1919}
1920
1921/*!
1922 \reimp
1923*/
1924qint64 QSslSocket::readData(char *data, qint64 maxlen)
1925{
1926 Q_D(QSslSocket);
1927 qint64 readBytes = 0;
1928
1929 if (d->mode == UnencryptedMode && !d->autoStartHandshake) {
1930 readBytes = d->plainSocket->read(data, maxlen);
1931#ifdef QSSLSOCKET_DEBUG
1932 qCDebug(lcSsl) << "QSslSocket::readData(" << (void *)data << ',' << maxlen << ") =="
1933 << readBytes;
1934#endif
1935 } else {
1936 // possibly trigger another transmit() to decrypt more data from the socket
1937 if (d->plainSocket->bytesAvailable() || d->hasUndecryptedData())
1938 QMetaObject::invokeMethod(this, "_q_flushReadBuffer", Qt::QueuedConnection);
1939 else if (d->state != QAbstractSocket::ConnectedState)
1940 return maxlen ? qint64(-1) : qint64(0);
1941 }
1942
1943 return readBytes;
1944}
1945
1946/*!
1947 \reimp
1948*/
1949qint64 QSslSocket::writeData(const char *data, qint64 len)
1950{
1951 Q_D(QSslSocket);
1952#ifdef QSSLSOCKET_DEBUG
1953 qCDebug(lcSsl) << "QSslSocket::writeData(" << (void *)data << ',' << len << ')';
1954#endif
1955 if (d->mode == UnencryptedMode && !d->autoStartHandshake)
1956 return d->plainSocket->write(data, len);
1957
1958 d->write(data, len);
1959
1960 // make sure we flush to the plain socket's buffer
1961 if (!d->flushTriggered) {
1962 d->flushTriggered = true;
1963 QMetaObject::invokeMethod(this, "_q_flushWriteBuffer", Qt::QueuedConnection);
1964 }
1965
1966 return len;
1967}
1968
1969bool QSslSocketPrivate::s_loadRootCertsOnDemand = false;
1970
1971/*!
1972 \internal
1973*/
1974QSslSocketPrivate::QSslSocketPrivate()
1975 : initialized(false)
1976 , mode(QSslSocket::UnencryptedMode)
1977 , autoStartHandshake(false)
1978 , connectionEncrypted(false)
1979 , ignoreAllSslErrors(false)
1980 , readyReadEmittedPointer(nullptr)
1981 , allowRootCertOnDemandLoading(true)
1982 , plainSocket(nullptr)
1983 , paused(false)
1984 , flushTriggered(false)
1985{
1986 QSslConfigurationPrivate::deepCopyDefaultConfiguration(&configuration);
1987 // If the global configuration doesn't allow root certificates to be loaded
1988 // on demand then we have to disable it for this socket as well.
1989 if (!configuration.allowRootCertOnDemandLoading)
1990 allowRootCertOnDemandLoading = false;
1991
1992 const auto *tlsBackend = tlsBackendInUse();
1993 if (!tlsBackend) {
1994 qCWarning(lcSsl, "No TLS backend is available");
1995 return;
1996 }
1997 backend.reset(tlsBackend->createTlsCryptograph());
1998 if (!backend.get()) {
1999 qCWarning(lcSsl) << "The backend named" << tlsBackend->backendName()
2000 << "does not support TLS";
2001 }
2002}
2003
2004/*!
2005 \internal
2006*/
2007QSslSocketPrivate::~QSslSocketPrivate()
2008{
2009}
2010
2011/*!
2012 \internal
2013*/
2014bool QSslSocketPrivate::supportsSsl()
2015{
2016 if (const auto *tlsBackend = tlsBackendInUse())
2017 return tlsBackend->implementedClasses().contains(QSsl::ImplementedClass::Socket);
2018 return false;
2019}
2020
2021/*!
2022 \internal
2023
2024 Declared static in QSslSocketPrivate, makes sure the SSL libraries have
2025 been initialized.
2026*/
2027void QSslSocketPrivate::ensureInitialized()
2028{
2029 if (!supportsSsl())
2030 return;
2031
2032 const auto *tlsBackend = tlsBackendInUse();
2033 Q_ASSERT(tlsBackend);
2034 tlsBackend->ensureInitialized();
2035}
2036
2037/*!
2038 \internal
2039*/
2040void QSslSocketPrivate::init()
2041{
2042 // TLSTODO: delete those data members.
2043 mode = QSslSocket::UnencryptedMode;
2044 autoStartHandshake = false;
2045 connectionEncrypted = false;
2046 ignoreAllSslErrors = false;
2047 abortCalled = false;
2048 pendingClose = false;
2049 flushTriggered = false;
2050 // We don't want to clear the ignoreErrorsList, so
2051 // that it is possible setting it before connecting.
2052
2053 buffer.clear();
2054 writeBuffer.clear();
2055 configuration.peerCertificate.clear();
2056 configuration.peerCertificateChain.clear();
2057
2058 if (backend.get()) {
2059 Q_ASSERT(q_ptr);
2060 backend->init(static_cast<QSslSocket *>(q_ptr), this);
2061 }
2062}
2063
2064/*!
2065 \internal
2066*/
2067bool QSslSocketPrivate::verifyProtocolSupported(const char *where)
2068{
2069 auto protocolName = "DTLS"_L1;
2070 switch (configuration.protocol) {
2071 case QSsl::UnknownProtocol:
2072 // UnknownProtocol, according to our docs, is for cipher whose protocol is unknown.
2073 // Should not be used when configuring QSslSocket.
2074 protocolName = "UnknownProtocol"_L1;
2075 Q_FALLTHROUGH();
2076QT_WARNING_PUSH
2077QT_WARNING_DISABLE_DEPRECATED
2078 case QSsl::DtlsV1_0:
2079 case QSsl::DtlsV1_2:
2080 case QSsl::DtlsV1_0OrLater:
2081 case QSsl::DtlsV1_2OrLater:
2082 qCWarning(lcSsl) << where << "QSslConfiguration with unexpected protocol" << protocolName;
2083 setErrorAndEmit(QAbstractSocket::SslInvalidUserDataError,
2084 QSslSocket::tr("Attempted to use an unsupported protocol."));
2085 return false;
2086QT_WARNING_POP
2087 default:
2088 return true;
2089 }
2090}
2091
2092/*!
2093 \internal
2094*/
2095QList<QSslCipher> QSslSocketPrivate::defaultCiphers()
2096{
2097 QSslSocketPrivate::ensureInitialized();
2098 QMutexLocker locker(&globalData()->mutex);
2099 return globalData()->config->ciphers;
2100}
2101
2102/*!
2103 \internal
2104*/
2105QList<QSslCipher> QSslSocketPrivate::supportedCiphers()
2106{
2107 QSslSocketPrivate::ensureInitialized();
2108 QMutexLocker locker(&globalData()->mutex);
2109 return globalData()->supportedCiphers;
2110}
2111
2112/*!
2113 \internal
2114*/
2115void QSslSocketPrivate::setDefaultCiphers(const QList<QSslCipher> &ciphers)
2116{
2117 QMutexLocker locker(&globalData()->mutex);
2118 globalData()->config.detach();
2119 globalData()->config->ciphers = ciphers;
2120}
2121
2122/*!
2123 \internal
2124*/
2125void QSslSocketPrivate::setDefaultSupportedCiphers(const QList<QSslCipher> &ciphers)
2126{
2127 QMutexLocker locker(&globalData()->mutex);
2128 globalData()->config.detach();
2129 globalData()->supportedCiphers = ciphers;
2130}
2131
2132/*!
2133 \internal
2134*/
2135void QSslSocketPrivate::resetDefaultEllipticCurves()
2136{
2137 const auto *tlsBackend = tlsBackendInUse();
2138 if (!tlsBackend)
2139 return;
2140
2141 auto ids = tlsBackend->ellipticCurvesIds();
2142 if (!ids.size())
2143 return;
2144
2145 QList<QSslEllipticCurve> curves;
2146 curves.reserve(ids.size());
2147 for (int id : ids) {
2148 QSslEllipticCurve curve;
2149 curve.id = id;
2150 curves.append(curve);
2151 }
2152
2153 // Set the list of supported ECs, but not the list
2154 // of *default* ECs. OpenSSL doesn't like forcing an EC for the wrong
2155 // ciphersuite, so don't try it -- leave the empty list to mean
2156 // "the implementation will choose the most suitable one".
2157 setDefaultSupportedEllipticCurves(curves);
2158}
2159
2160/*!
2161 \internal
2162*/
2163void QSslSocketPrivate::setDefaultDtlsCiphers(const QList<QSslCipher> &ciphers)
2164{
2165 QMutexLocker locker(&globalData()->mutex);
2166 globalData()->dtlsConfig.detach();
2167 globalData()->dtlsConfig->ciphers = ciphers;
2168}
2169
2170/*!
2171 \internal
2172*/
2173QList<QSslCipher> QSslSocketPrivate::defaultDtlsCiphers()
2174{
2175 QSslSocketPrivate::ensureInitialized();
2176 QMutexLocker locker(&globalData()->mutex);
2177 return globalData()->dtlsConfig->ciphers;
2178}
2179
2180/*!
2181 \internal
2182*/
2183QList<QSslEllipticCurve> QSslSocketPrivate::supportedEllipticCurves()
2184{
2185 QSslSocketPrivate::ensureInitialized();
2186 const QMutexLocker locker(&globalData()->mutex);
2187 return globalData()->supportedEllipticCurves;
2188}
2189
2190/*!
2191 \internal
2192*/
2193void QSslSocketPrivate::setDefaultSupportedEllipticCurves(const QList<QSslEllipticCurve> &curves)
2194{
2195 const QMutexLocker locker(&globalData()->mutex);
2196 globalData()->config.detach();
2197 globalData()->dtlsConfig.detach();
2198 globalData()->supportedEllipticCurves = curves;
2199}
2200
2201/*!
2202 \internal
2203*/
2204QList<QSslCertificate> QSslSocketPrivate::defaultCaCertificates()
2205{
2206 QSslSocketPrivate::ensureInitialized();
2207 QMutexLocker locker(&globalData()->mutex);
2208 return globalData()->config->caCertificates;
2209}
2210
2211/*!
2212 \internal
2213*/
2214void QSslSocketPrivate::setDefaultCaCertificates(const QList<QSslCertificate> &certs)
2215{
2216 QSslSocketPrivate::ensureInitialized();
2217 QMutexLocker locker(&globalData()->mutex);
2218 globalData()->config.detach();
2219 globalData()->config->caCertificates = certs;
2220 globalData()->dtlsConfig.detach();
2221 globalData()->dtlsConfig->caCertificates = certs;
2222 // when the certificates are set explicitly, we do not want to
2223 // load the system certificates on demand
2224 s_loadRootCertsOnDemand = false;
2225}
2226
2227/*!
2228 \internal
2229*/
2230void QSslSocketPrivate::addDefaultCaCertificate(const QSslCertificate &cert)
2231{
2232 QSslSocketPrivate::ensureInitialized();
2233 QMutexLocker locker(&globalData()->mutex);
2234 if (globalData()->config->caCertificates.contains(cert))
2235 return;
2236 globalData()->config.detach();
2237 globalData()->config->caCertificates += cert;
2238 globalData()->dtlsConfig.detach();
2239 globalData()->dtlsConfig->caCertificates += cert;
2240}
2241
2242/*!
2243 \internal
2244*/
2245void QSslSocketPrivate::addDefaultCaCertificates(const QList<QSslCertificate> &certs)
2246{
2247 QSslSocketPrivate::ensureInitialized();
2248 QMutexLocker locker(&globalData()->mutex);
2249 globalData()->config.detach();
2250 globalData()->config->caCertificates += certs;
2251 globalData()->dtlsConfig.detach();
2252 globalData()->dtlsConfig->caCertificates += certs;
2253}
2254
2255/*!
2256 \internal
2257*/
2258QSslConfiguration QSslConfigurationPrivate::defaultConfiguration()
2259{
2260 QSslSocketPrivate::ensureInitialized();
2261 QMutexLocker locker(&globalData()->mutex);
2262 return QSslConfiguration(globalData()->config.data());
2263}
2264
2265/*!
2266 \internal
2267*/
2268void QSslConfigurationPrivate::setDefaultConfiguration(const QSslConfiguration &configuration)
2269{
2270 QSslSocketPrivate::ensureInitialized();
2271 QMutexLocker locker(&globalData()->mutex);
2272 if (globalData()->config == configuration.d)
2273 return; // nothing to do
2274
2275 globalData()->config = const_cast<QSslConfigurationPrivate*>(configuration.d.constData());
2276}
2277
2278/*!
2279 \internal
2280*/
2281void QSslConfigurationPrivate::deepCopyDefaultConfiguration(QSslConfigurationPrivate *ptr)
2282{
2283 QSslSocketPrivate::ensureInitialized();
2284 QMutexLocker locker(&globalData()->mutex);
2285 const QSslConfigurationPrivate *global = globalData()->config.constData();
2286
2287 if (!global)
2288 return;
2289
2290 ptr->ref.storeRelaxed(1);
2291 ptr->peerCertificate = global->peerCertificate;
2292 ptr->peerCertificateChain = global->peerCertificateChain;
2293 ptr->localCertificateChain = global->localCertificateChain;
2294 ptr->privateKey = global->privateKey;
2295 ptr->sessionCipher = global->sessionCipher;
2296 ptr->sessionProtocol = global->sessionProtocol;
2297 ptr->ciphers = global->ciphers;
2298 ptr->caCertificates = global->caCertificates;
2299 ptr->allowRootCertOnDemandLoading = global->allowRootCertOnDemandLoading;
2300 ptr->protocol = global->protocol;
2301 ptr->peerVerifyMode = global->peerVerifyMode;
2302 ptr->peerVerifyDepth = global->peerVerifyDepth;
2303 ptr->sslOptions = global->sslOptions;
2304 ptr->ellipticCurves = global->ellipticCurves;
2305 ptr->backendConfig = global->backendConfig;
2306#if QT_CONFIG(dtls)
2307 ptr->dtlsCookieEnabled = global->dtlsCookieEnabled;
2308#endif
2309#if QT_CONFIG(ocsp)
2310 ptr->ocspStaplingEnabled = global->ocspStaplingEnabled;
2311#endif
2312#if QT_CONFIG(openssl)
2313 ptr->reportFromCallback = global->reportFromCallback;
2314 ptr->missingCertIsFatal = global->missingCertIsFatal;
2315#endif
2316}
2317
2318/*!
2319 \internal
2320*/
2321QSslConfiguration QSslConfigurationPrivate::defaultDtlsConfiguration()
2322{
2323 QSslSocketPrivate::ensureInitialized();
2324 QMutexLocker locker(&globalData()->mutex);
2325
2326 return QSslConfiguration(globalData()->dtlsConfig.data());
2327}
2328
2329/*!
2330 \internal
2331*/
2332void QSslConfigurationPrivate::setDefaultDtlsConfiguration(const QSslConfiguration &configuration)
2333{
2334 QSslSocketPrivate::ensureInitialized();
2335 QMutexLocker locker(&globalData()->mutex);
2336 if (globalData()->dtlsConfig == configuration.d)
2337 return; // nothing to do
2338
2339 globalData()->dtlsConfig = const_cast<QSslConfigurationPrivate*>(configuration.d.constData());
2340}
2341
2342/*!
2343 \internal
2344*/
2345void QSslSocketPrivate::createPlainSocket(QIODevice::OpenMode openMode)
2346{
2347 Q_Q(QSslSocket);
2348 q->setOpenMode(openMode); // <- from QIODevice
2349 q->setSocketState(QAbstractSocket::UnconnectedState);
2350 q->setSocketError(QAbstractSocket::UnknownSocketError);
2351 q->setLocalPort(0);
2352 q->setLocalAddress(QHostAddress());
2353 q->setPeerPort(0);
2354 q->setPeerAddress(QHostAddress());
2355 q->setPeerName(QString());
2356
2357 plainSocket = new QTcpSocket(q);
2358 q->connect(plainSocket, SIGNAL(connected()),
2359 q, SLOT(_q_connectedSlot()),
2360 Qt::DirectConnection);
2361 q->connect(plainSocket, SIGNAL(hostFound()),
2362 q, SLOT(_q_hostFoundSlot()),
2363 Qt::DirectConnection);
2364 q->connect(plainSocket, SIGNAL(disconnected()),
2365 q, SLOT(_q_disconnectedSlot()),
2366 Qt::DirectConnection);
2367 q->connect(plainSocket, SIGNAL(stateChanged(QAbstractSocket::SocketState)),
2368 q, SLOT(_q_stateChangedSlot(QAbstractSocket::SocketState)),
2369 Qt::DirectConnection);
2370 q->connect(plainSocket, SIGNAL(errorOccurred(QAbstractSocket::SocketError)),
2371 q, SLOT(_q_errorSlot(QAbstractSocket::SocketError)),
2372 Qt::DirectConnection);
2373 q->connect(plainSocket, SIGNAL(readyRead()),
2374 q, SLOT(_q_readyReadSlot()),
2375 Qt::DirectConnection);
2376 q->connect(plainSocket, SIGNAL(channelReadyRead(int)),
2377 q, SLOT(_q_channelReadyReadSlot(int)),
2378 Qt::DirectConnection);
2379 q->connect(plainSocket, SIGNAL(bytesWritten(qint64)),
2380 q, SLOT(_q_bytesWrittenSlot(qint64)),
2381 Qt::DirectConnection);
2382 q->connect(plainSocket, SIGNAL(channelBytesWritten(int,qint64)),
2383 q, SLOT(_q_channelBytesWrittenSlot(int,qint64)),
2384 Qt::DirectConnection);
2385 q->connect(plainSocket, SIGNAL(readChannelFinished()),
2386 q, SLOT(_q_readChannelFinishedSlot()),
2387 Qt::DirectConnection);
2388#ifndef QT_NO_NETWORKPROXY
2389 q->connect(plainSocket, SIGNAL(proxyAuthenticationRequired(QNetworkProxy,QAuthenticator*)),
2390 q, SIGNAL(proxyAuthenticationRequired(QNetworkProxy,QAuthenticator*)));
2391#endif
2392
2393 buffer.clear();
2394 writeBuffer.clear();
2395 connectionEncrypted = false;
2396 configuration.peerCertificate.clear();
2397 configuration.peerCertificateChain.clear();
2398 mode = QSslSocket::UnencryptedMode;
2399 q->setReadBufferSize(readBufferMaxSize);
2400}
2401
2402void QSslSocketPrivate::pauseSocketNotifiers(QSslSocket *socket)
2403{
2404 if (!socket->d_func()->plainSocket)
2405 return;
2406 QAbstractSocketPrivate::pauseSocketNotifiers(socket->d_func()->plainSocket);
2407}
2408
2409void QSslSocketPrivate::resumeSocketNotifiers(QSslSocket *socket)
2410{
2411 if (!socket->d_func()->plainSocket)
2412 return;
2413 QAbstractSocketPrivate::resumeSocketNotifiers(socket->d_func()->plainSocket);
2414}
2415
2416bool QSslSocketPrivate::isPaused() const
2417{
2418 return paused;
2419}
2420
2421void QSslSocketPrivate::setPaused(bool p)
2422{
2423 paused = p;
2424}
2425
2426bool QSslSocketPrivate::bind(const QHostAddress &address, quint16 port, QAbstractSocket::BindMode mode,
2427 const QNetworkInterface *iface)
2428{
2429 Q_UNUSED(iface); // only relevant for QUdpSocket for now
2430 // this function is called from QAbstractSocket::bind
2431 if (!initialized)
2432 init();
2433 initialized = false;
2434
2435#ifdef QSSLSOCKET_DEBUG
2436 qCDebug(lcSsl) << "QSslSocket::bind(" << address << ',' << port << ',' << mode << ')';
2437#endif
2438 if (!plainSocket) {
2439#ifdef QSSLSOCKET_DEBUG
2440 qCDebug(lcSsl) << "\tcreating internal plain socket";
2441#endif
2442 createPlainSocket(QIODevice::ReadWrite);
2443 }
2444 bool ret = plainSocket->bind(address, port, mode);
2445 localPort = plainSocket->localPort();
2446 localAddress = plainSocket->localAddress();
2447 cachedSocketDescriptor = plainSocket->socketDescriptor();
2448 readChannelCount = writeChannelCount = 0;
2449 return ret;
2450}
2451
2452/*!
2453 \internal
2454*/
2455void QSslSocketPrivate::_q_connectedSlot()
2456{
2457 Q_Q(QSslSocket);
2458 q->setLocalPort(plainSocket->localPort());
2459 q->setLocalAddress(plainSocket->localAddress());
2460 q->setPeerPort(plainSocket->peerPort());
2461 q->setPeerAddress(plainSocket->peerAddress());
2462 q->setPeerName(plainSocket->peerName());
2463 cachedSocketDescriptor = plainSocket->socketDescriptor();
2464 readChannelCount = plainSocket->readChannelCount();
2465 writeChannelCount = plainSocket->writeChannelCount();
2466
2467#ifdef QSSLSOCKET_DEBUG
2468 qCDebug(lcSsl) << "QSslSocket::_q_connectedSlot()";
2469 qCDebug(lcSsl) << "\tstate =" << q->state();
2470 qCDebug(lcSsl) << "\tpeer =" << q->peerName() << q->peerAddress() << q->peerPort();
2471 qCDebug(lcSsl) << "\tlocal =" << QHostInfo::fromName(q->localAddress().toString()).hostName()
2472 << q->localAddress() << q->localPort();
2473#endif
2474
2475 if (autoStartHandshake)
2476 q->startClientEncryption();
2477
2478 emit q->connected();
2479
2480 if (pendingClose && !autoStartHandshake) {
2481 pendingClose = false;
2482 q->disconnectFromHost();
2483 }
2484}
2485
2486/*!
2487 \internal
2488*/
2489void QSslSocketPrivate::_q_hostFoundSlot()
2490{
2491 Q_Q(QSslSocket);
2492#ifdef QSSLSOCKET_DEBUG
2493 qCDebug(lcSsl) << "QSslSocket::_q_hostFoundSlot()";
2494 qCDebug(lcSsl) << "\tstate =" << q->state();
2495#endif
2496 emit q->hostFound();
2497}
2498
2499/*!
2500 \internal
2501*/
2502void QSslSocketPrivate::_q_disconnectedSlot()
2503{
2504 Q_Q(QSslSocket);
2505#ifdef QSSLSOCKET_DEBUG
2506 qCDebug(lcSsl) << "QSslSocket::_q_disconnectedSlot()";
2507 qCDebug(lcSsl) << "\tstate =" << q->state();
2508#endif
2509 disconnected();
2510 emit q->disconnected();
2511
2512 q->setLocalPort(0);
2513 q->setLocalAddress(QHostAddress());
2514 q->setPeerPort(0);
2515 q->setPeerAddress(QHostAddress());
2516 q->setPeerName(QString());
2517 cachedSocketDescriptor = -1;
2518}
2519
2520/*!
2521 \internal
2522*/
2523void QSslSocketPrivate::_q_stateChangedSlot(QAbstractSocket::SocketState state)
2524{
2525 Q_Q(QSslSocket);
2526#ifdef QSSLSOCKET_DEBUG
2527 qCDebug(lcSsl) << "QSslSocket::_q_stateChangedSlot(" << state << ')';
2528#endif
2529 q->setSocketState(state);
2530 emit q->stateChanged(state);
2531}
2532
2533/*!
2534 \internal
2535*/
2536void QSslSocketPrivate::_q_errorSlot(QAbstractSocket::SocketError error)
2537{
2538 Q_UNUSED(error);
2539#ifdef QSSLSOCKET_DEBUG
2540 Q_Q(QSslSocket);
2541 qCDebug(lcSsl) << "QSslSocket::_q_errorSlot(" << error << ')';
2542 qCDebug(lcSsl) << "\tstate =" << q->state();
2543 qCDebug(lcSsl) << "\terrorString =" << q->errorString();
2544#endif
2545 // this moves encrypted bytes from plain socket into our buffer
2546 if (plainSocket->bytesAvailable() && mode != QSslSocket::UnencryptedMode) {
2547 qint64 tmpReadBufferMaxSize = readBufferMaxSize;
2548 readBufferMaxSize = 0; // reset temporarily so the plain sockets completely drained drained
2549 transmit();
2550 readBufferMaxSize = tmpReadBufferMaxSize;
2551 }
2552
2553 setErrorAndEmit(plainSocket->error(), plainSocket->errorString());
2554}
2555
2556/*!
2557 \internal
2558*/
2559void QSslSocketPrivate::_q_readyReadSlot()
2560{
2561 Q_Q(QSslSocket);
2562#ifdef QSSLSOCKET_DEBUG
2563 qCDebug(lcSsl) << "QSslSocket::_q_readyReadSlot() -" << plainSocket->bytesAvailable() << "bytes available";
2564#endif
2565 if (mode == QSslSocket::UnencryptedMode) {
2566 if (readyReadEmittedPointer)
2567 *readyReadEmittedPointer = true;
2568 emit q->readyRead();
2569 return;
2570 }
2571
2572 transmit();
2573}
2574
2575/*!
2576 \internal
2577*/
2578void QSslSocketPrivate::_q_channelReadyReadSlot(int channel)
2579{
2580 Q_Q(QSslSocket);
2581 if (mode == QSslSocket::UnencryptedMode)
2582 emit q->channelReadyRead(channel);
2583}
2584
2585/*!
2586 \internal
2587*/
2588void QSslSocketPrivate::_q_bytesWrittenSlot(qint64 written)
2589{
2590 Q_Q(QSslSocket);
2591#ifdef QSSLSOCKET_DEBUG
2592 qCDebug(lcSsl) << "QSslSocket::_q_bytesWrittenSlot(" << written << ')';
2593#endif
2594
2595 if (mode == QSslSocket::UnencryptedMode)
2596 emit q->bytesWritten(written);
2597 else
2598 emit q->encryptedBytesWritten(written);
2599 if (state == QAbstractSocket::ClosingState && writeBuffer.isEmpty())
2600 q->disconnectFromHost();
2601}
2602
2603/*!
2604 \internal
2605*/
2606void QSslSocketPrivate::_q_channelBytesWrittenSlot(int channel, qint64 written)
2607{
2608 Q_Q(QSslSocket);
2609 if (mode == QSslSocket::UnencryptedMode)
2610 emit q->channelBytesWritten(channel, written);
2611}
2612
2613/*!
2614 \internal
2615*/
2616void QSslSocketPrivate::_q_readChannelFinishedSlot()
2617{
2618 Q_Q(QSslSocket);
2619 emit q->readChannelFinished();
2620}
2621
2622/*!
2623 \internal
2624*/
2625void QSslSocketPrivate::_q_flushWriteBuffer()
2626{
2627 Q_Q(QSslSocket);
2628
2629 // need to notice if knock-on effects of this flush (e.g. a readReady() via transmit())
2630 // make another necessary, so clear flag before calling:
2631 flushTriggered = false;
2632 if (!writeBuffer.isEmpty())
2633 q->flush();
2634}
2635
2636/*!
2637 \internal
2638*/
2639void QSslSocketPrivate::_q_flushReadBuffer()
2640{
2641 // trigger a read from the plainSocket into SSL
2642 if (mode != QSslSocket::UnencryptedMode)
2643 transmit();
2644}
2645
2646/*!
2647 \internal
2648*/
2649void QSslSocketPrivate::_q_resumeImplementation()
2650{
2651 if (plainSocket)
2652 plainSocket->resume();
2653 paused = false;
2654 if (!connectionEncrypted) {
2655 if (verifyErrorsHaveBeenIgnored()) {
2656 continueHandshake();
2657 } else {
2658 const auto sslErrors = backend->tlsErrors();
2659 Q_ASSERT(!sslErrors.isEmpty());
2660 setErrorAndEmit(QAbstractSocket::SslHandshakeFailedError, sslErrors.constFirst().errorString());
2661 plainSocket->disconnectFromHost();
2662 return;
2663 }
2664 }
2665 transmit();
2666}
2667
2668/*!
2669 \internal
2670*/
2671bool QSslSocketPrivate::verifyErrorsHaveBeenIgnored()
2672{
2673 Q_ASSERT(backend.get());
2674
2675 bool doEmitSslError;
2676 if (!ignoreErrorsList.empty()) {
2677 // check whether the errors we got are all in the list of expected errors
2678 // (applies only if the method QSslSocket::ignoreSslErrors(const QList<QSslError> &errors)
2679 // was called)
2680 const auto &sslErrors = backend->tlsErrors();
2681 doEmitSslError = false;
2682 for (int a = 0; a < sslErrors.size(); a++) {
2683 if (!ignoreErrorsList.contains(sslErrors.at(a))) {
2684 doEmitSslError = true;
2685 break;
2686 }
2687 }
2688 } else {
2689 // if QSslSocket::ignoreSslErrors(const QList<QSslError> &errors) was not called and
2690 // we get an SSL error, emit a signal unless we ignored all errors (by calling
2691 // QSslSocket::ignoreSslErrors() )
2692 doEmitSslError = !ignoreAllSslErrors;
2693 }
2694 return !doEmitSslError;
2695}
2696
2697/*!
2698 \internal
2699*/
2700bool QSslSocketPrivate::isAutoStartingHandshake() const
2701{
2702 return autoStartHandshake;
2703}
2704
2705/*!
2706 \internal
2707*/
2708bool QSslSocketPrivate::isPendingClose() const
2709{
2710 return pendingClose;
2711}
2712
2713/*!
2714 \internal
2715*/
2716void QSslSocketPrivate::setPendingClose(bool pc)
2717{
2718 pendingClose = pc;
2719}
2720
2721/*!
2722 \internal
2723*/
2724qint64 QSslSocketPrivate::maxReadBufferSize() const
2725{
2726 return readBufferMaxSize;
2727}
2728
2729/*!
2730 \internal
2731*/
2732void QSslSocketPrivate::setMaxReadBufferSize(qint64 maxSize)
2733{
2734 readBufferMaxSize = maxSize;
2735}
2736
2737/*!
2738 \internal
2739*/
2740void QSslSocketPrivate::setEncrypted(bool enc)
2741{
2742 connectionEncrypted = enc;
2743}
2744
2745/*!
2746 \internal
2747*/
2748QIODevicePrivate::QRingBufferRef &QSslSocketPrivate::tlsWriteBuffer()
2749{
2750 return writeBuffer;
2751}
2752
2753/*!
2754 \internal
2755*/
2756QIODevicePrivate::QRingBufferRef &QSslSocketPrivate::tlsBuffer()
2757{
2758 return buffer;
2759}
2760
2761/*!
2762 \internal
2763*/
2764bool &QSslSocketPrivate::tlsEmittedBytesWritten()
2765{
2766 return emittedBytesWritten;
2767}
2768
2769/*!
2770 \internal
2771*/
2772bool *QSslSocketPrivate::readyReadPointer()
2773{
2774 return readyReadEmittedPointer;
2775}
2776
2777bool QSslSocketPrivate::hasUndecryptedData() const
2778{
2779 return backend.get() && backend->hasUndecryptedData();
2780}
2781
2782/*!
2783 \internal
2784*/
2785qint64 QSslSocketPrivate::peek(char *data, qint64 maxSize)
2786{
2787 if (mode == QSslSocket::UnencryptedMode && !autoStartHandshake) {
2788 //unencrypted mode - do not use QIODevice::peek, as it reads ahead data from the plain socket
2789 //peek at data already in the QIODevice buffer (from a previous read)
2790 qint64 r = buffer.peek(data, maxSize, transactionPos);
2791 if (r == maxSize)
2792 return r;
2793 data += r;
2794 //peek at data in the plain socket
2795 if (plainSocket) {
2796 qint64 r2 = plainSocket->peek(data, maxSize - r);
2797 if (r2 < 0)
2798 return (r > 0 ? r : r2);
2799 return r + r2;
2800 }
2801
2802 return -1;
2803 } else {
2804 //encrypted mode - the socket engine will read and decrypt data into the QIODevice buffer
2805 return QTcpSocketPrivate::peek(data, maxSize);
2806 }
2807}
2808
2809/*!
2810 \internal
2811*/
2812QByteArray QSslSocketPrivate::peek(qint64 maxSize)
2813{
2814 if (mode == QSslSocket::UnencryptedMode && !autoStartHandshake) {
2815 //unencrypted mode - do not use QIODevice::peek, as it reads ahead data from the plain socket
2816 //peek at data already in the QIODevice buffer (from a previous read)
2817 QByteArray ret;
2818 ret.reserve(maxSize);
2819 ret.resize(buffer.peek(ret.data(), maxSize, transactionPos));
2820 if (ret.size() == maxSize)
2821 return ret;
2822 //peek at data in the plain socket
2823 if (plainSocket)
2824 return ret + plainSocket->peek(maxSize - ret.size());
2825
2826 return QByteArray();
2827 } else {
2828 //encrypted mode - the socket engine will read and decrypt data into the QIODevice buffer
2829 return QTcpSocketPrivate::peek(maxSize);
2830 }
2831}
2832
2833/*!
2834 \reimp
2835*/
2836qint64 QSslSocket::skipData(qint64 maxSize)
2837{
2838 Q_D(QSslSocket);
2839
2840 if (d->mode == QSslSocket::UnencryptedMode && !d->autoStartHandshake)
2841 return d->plainSocket->skip(maxSize);
2842
2843 // In encrypted mode, the SSL backend writes decrypted data directly into the
2844 // QIODevice's read buffer. As this buffer is always emptied by the caller,
2845 // we need to wait for more incoming data.
2846 return (d->state == QAbstractSocket::ConnectedState) ? Q_INT64_C(0) : Q_INT64_C(-1);
2847}
2848
2849/*!
2850 \internal
2851*/
2852bool QSslSocketPrivate::flush()
2853{
2854#ifdef QSSLSOCKET_DEBUG
2855 qCDebug(lcSsl) << "QSslSocketPrivate::flush()";
2856#endif
2857 if (mode != QSslSocket::UnencryptedMode) {
2858 // encrypt any unencrypted bytes in our buffer
2859 transmit();
2860 }
2861
2862 return plainSocket && plainSocket->flush();
2863}
2864
2865/*!
2866 \internal
2867*/
2868void QSslSocketPrivate::startClientEncryption()
2869{
2870 if (backend.get())
2871 backend->startClientEncryption();
2872}
2873
2874/*!
2875 \internal
2876*/
2877void QSslSocketPrivate::startServerEncryption()
2878{
2879 if (backend.get())
2880 backend->startServerEncryption();
2881}
2882
2883/*!
2884 \internal
2885*/
2886void QSslSocketPrivate::transmit()
2887{
2888 if (backend.get())
2889 backend->transmit();
2890}
2891
2892/*!
2893 \internal
2894*/
2895void QSslSocketPrivate::disconnectFromHost()
2896{
2897 if (backend.get())
2898 backend->disconnectFromHost();
2899}
2900
2901/*!
2902 \internal
2903*/
2904void QSslSocketPrivate::disconnected()
2905{
2906 if (backend.get())
2907 backend->disconnected();
2908}
2909
2910/*!
2911 \internal
2912*/
2913QSslCipher QSslSocketPrivate::sessionCipher() const
2914{
2915 if (backend.get())
2916 return backend->sessionCipher();
2917
2918 return {};
2919}
2920
2921/*!
2922 \internal
2923*/
2924QSsl::SslProtocol QSslSocketPrivate::sessionProtocol() const
2925{
2926 if (backend.get())
2927 return backend->sessionProtocol();
2928
2929 return QSsl::UnknownProtocol;
2930}
2931
2932/*!
2933 \internal
2934*/
2935void QSslSocketPrivate::continueHandshake()
2936{
2937 if (backend.get())
2938 backend->continueHandshake();
2939}
2940
2941/*!
2942 \internal
2943*/
2944bool QSslSocketPrivate::rootCertOnDemandLoadingSupported()
2945{
2946 return s_loadRootCertsOnDemand;
2947}
2948
2949/*!
2950 \internal
2951*/
2952void QSslSocketPrivate::setRootCertOnDemandLoadingSupported(bool supported)
2953{
2954 s_loadRootCertsOnDemand = supported;
2955}
2956
2957/*!
2958 \internal
2959*/
2960QList<QByteArray> QSslSocketPrivate::unixRootCertDirectories()
2961{
2962 const auto ba = [](const auto &cstr) constexpr {
2963 return QByteArray::fromRawData(std::begin(cstr), std::size(cstr) - 1);
2964 };
2965 static const QByteArray dirs[] = {
2966 ba("/etc/ssl/certs/"), // (K)ubuntu, OpenSUSE, Mandriva ...
2967 ba("/usr/lib/ssl/certs/"), // Gentoo, Mandrake
2968 ba("/usr/share/ssl/"), // Red Hat pre-2004, SuSE
2969 ba("/etc/pki/ca-trust/extracted/pem/directory-hash/"), // Red Hat 2021+
2970 ba("/usr/local/ssl/"), // Normal OpenSSL Tarball
2971 ba("/var/ssl/certs/"), // AIX
2972 ba("/usr/local/ssl/certs/"), // Solaris
2973 ba("/etc/openssl/certs/"), // BlackBerry
2974 ba("/opt/openssl/certs/"), // HP-UX
2975 ba("/etc/ssl/"), // OpenBSD
2976 };
2977 QList<QByteArray> result = QList<QByteArray>::fromReadOnlyData(dirs);
2978 if constexpr (isVxworks) {
2979 static QByteArray vxworksCertsDir = qgetenv("VXWORKS_CERTS_DIR");
2980 if (!vxworksCertsDir.isEmpty())
2981 result.push_back(vxworksCertsDir);
2982 }
2983 return result;
2984}
2985
2986/*!
2987 \internal
2988*/
2989void QSslSocketPrivate::checkSettingSslContext(QSslSocket* socket, std::shared_ptr<QSslContext> tlsContext)
2990{
2991 if (!socket)
2992 return;
2993
2994 if (auto *backend = socket->d_func()->backend.get())
2995 backend->checkSettingSslContext(tlsContext);
2996}
2997
2998/*!
2999 \internal
3000*/
3001std::shared_ptr<QSslContext> QSslSocketPrivate::sslContext(QSslSocket *socket)
3002{
3003 if (!socket)
3004 return {};
3005
3006 if (const auto *backend = socket->d_func()->backend.get())
3007 return backend->sslContext();
3008
3009 return {};
3010}
3011
3012bool QSslSocketPrivate::isMatchingHostname(const QSslCertificate &cert, const QString &peerName)
3013{
3014 QHostAddress hostAddress(peerName);
3015 if (!hostAddress.isNull()) {
3016 const auto subjectAlternativeNames = cert.subjectAlternativeNames();
3017 const auto ipAddresses = subjectAlternativeNames.equal_range(QSsl::AlternativeNameEntryType::IpAddressEntry);
3018
3019 for (auto it = ipAddresses.first; it != ipAddresses.second; it++) {
3020 if (QHostAddress(*it).isEqual(hostAddress, QHostAddress::StrictConversion))
3021 return true;
3022 }
3023 }
3024
3025 const QString lowerPeerName = QString::fromLatin1(QUrl::toAce(peerName));
3026 const QStringList commonNames = cert.subjectInfo(QSslCertificate::CommonName);
3027
3028 for (const QString &commonName : commonNames) {
3029 if (isMatchingHostname(commonName, lowerPeerName))
3030 return true;
3031 }
3032
3033 const auto subjectAlternativeNames = cert.subjectAlternativeNames();
3034 const auto altNames = subjectAlternativeNames.equal_range(QSsl::DnsEntry);
3035 for (auto it = altNames.first; it != altNames.second; ++it) {
3036 if (isMatchingHostname(*it, lowerPeerName))
3037 return true;
3038 }
3039
3040 return false;
3041}
3042
3043/*! \internal
3044 Checks if the certificate's name \a cn matches the \a hostname.
3045 \a hostname must be normalized in ASCII-Compatible Encoding, but \a cn is not normalized
3046 */
3047bool QSslSocketPrivate::isMatchingHostname(const QString &cn, const QString &hostname)
3048{
3049 qsizetype wildcard = cn.indexOf(u'*');
3050
3051 // Check this is a wildcard cert, if not then just compare the strings
3052 if (wildcard < 0)
3053 return QLatin1StringView(QUrl::toAce(cn)) == hostname;
3054
3055 qsizetype firstCnDot = cn.indexOf(u'.');
3056 qsizetype secondCnDot = cn.indexOf(u'.', firstCnDot+1);
3057
3058 // Check at least 3 components
3059 if ((-1 == secondCnDot) || (secondCnDot+1 >= cn.size()))
3060 return false;
3061
3062 // Check * is last character of 1st component (ie. there's a following .)
3063 if (wildcard+1 != firstCnDot)
3064 return false;
3065
3066 // Check only one star
3067 if (cn.lastIndexOf(u'*') != wildcard)
3068 return false;
3069
3070 // Reject wildcard character embedded within the A-labels or U-labels of an internationalized
3071 // domain name (RFC6125 section 7.2)
3072 if (cn.startsWith("xn--"_L1, Qt::CaseInsensitive))
3073 return false;
3074
3075 // Check characters preceding * (if any) match
3076 if (wildcard && QStringView{hostname}.left(wildcard).compare(QStringView{cn}.left(wildcard), Qt::CaseInsensitive) != 0)
3077 return false;
3078
3079 // Check characters following first . match
3080 qsizetype hnDot = hostname.indexOf(u'.');
3081 if (QStringView{hostname}.mid(hnDot + 1) != QStringView{cn}.mid(firstCnDot + 1)
3082 && QStringView{hostname}.mid(hnDot + 1) != QLatin1StringView(QUrl::toAce(cn.mid(firstCnDot + 1)))) {
3083 return false;
3084 }
3085
3086 // Check if the hostname is an IP address, if so then wildcards are not allowed
3087 QHostAddress addr(hostname);
3088 if (!addr.isNull())
3089 return false;
3090
3091 // Ok, I guess this was a wildcard CN and the hostname matches.
3092 return true;
3093}
3094
3095/*!
3096 \internal
3097*/
3098QTlsBackend *QSslSocketPrivate::tlsBackendInUse()
3099{
3100 const QMutexLocker locker(&backendMutex);
3101 if (tlsBackend)
3102 return tlsBackend;
3103
3104 if (!activeBackendName.size())
3105 activeBackendName = QTlsBackend::defaultBackendName();
3106
3107 if (!activeBackendName.size()) {
3108 qCWarning(lcSsl, "No functional TLS backend was found");
3109 return nullptr;
3110 }
3111
3112 tlsBackend = QTlsBackend::findBackend(activeBackendName);
3113 if (tlsBackend) {
3114 QObject::connect(tlsBackend, &QObject::destroyed, tlsBackend, [] {
3115 const QMutexLocker locker(&backendMutex);
3116 tlsBackend = nullptr;
3117 },
3118 Qt::DirectConnection);
3119 }
3120 return tlsBackend;
3121}
3122
3123/*!
3124 \internal
3125*/
3126QSslSocket::SslMode QSslSocketPrivate::tlsMode() const
3127{
3128 return mode;
3129}
3130
3131/*!
3132 \internal
3133*/
3134bool QSslSocketPrivate::isRootsOnDemandAllowed() const
3135{
3136 return allowRootCertOnDemandLoading;
3137}
3138
3139/*!
3140 \internal
3141*/
3142QString QSslSocketPrivate::verificationName() const
3143{
3144 return verificationPeerName;
3145}
3146
3147/*!
3148 \internal
3149*/
3150QString QSslSocketPrivate::tlsHostName() const
3151{
3152 return hostName;
3153}
3154
3155QTcpSocket *QSslSocketPrivate::plainTcpSocket() const
3156{
3157 return plainSocket;
3158}
3159
3160/*!
3161 \internal
3162*/
3163QList<QSslCertificate> QSslSocketPrivate::systemCaCertificates()
3164{
3165 if (const auto *tlsBackend = tlsBackendInUse())
3166 return tlsBackend->systemCaCertificates();
3167 return {};
3168}
3169
3170QT_END_NAMESPACE
3171
3172#include "moc_qsslsocket.cpp"
Definition qlist.h:80
Represents an elliptic curve for use by elliptic-curve cipher algorithms.
QList< QSslCipher > supportedCiphers
QList< QSslEllipticCurve > supportedEllipticCurves
QExplicitlySharedDataPointer< QSslConfigurationPrivate > dtlsConfig
QExplicitlySharedDataPointer< QSslConfigurationPrivate > config
constexpr auto isVxworks