1 /*
2  * qca_securelayer.h - Qt Cryptographic Architecture
3  * Copyright (C) 2003-2007  Justin Karneges <justin@affinix.com>
4  * Copyright (C) 2004-2006  Brad Hards <bradh@frogmouth.net>
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19  * 02110-1301  USA
20  *
21  */
22 
23 /**
24    \file qca_securelayer.h
25 
26    Header file for SecureLayer and its subclasses
27 
28    \note You should not use this header directly from an
29    application. You should just use <tt> \#include \<QtCrypto>
30    </tt> instead.
31 */
32 #ifndef QCA_SECURELAYER_H
33 #define QCA_SECURELAYER_H
34 
35 #include "qca_cert.h"
36 #include "qca_core.h"
37 #include "qca_publickey.h"
38 #include <QObject>
39 
40 namespace QCA {
41 
42 /**
43    Specify the lower-bound for acceptable TLS/SASL security layers
44 
45    For TLS, the interpretation of these levels is:
46    - Any cipher suite that provides non-authenticated communications
47    (usually anonymous Diffie-Hellman) is SL_Integrity.
48    - Any cipher suite that is limited to 40 bits (export-version
49    crippled forms of RC2, RC4 or DES) is SL_Export. Standard
50    DES (56 bits) and some forms of RC4 (64 bits) are also SL_Export.
51    - Any normal cipher (AES, Camellia, RC4 or similar) with 128 bits, or
52    Elliptic Curve Ciphers with 283 bits, is SL_Baseline
53    - AES or Camellia at least 192 bits, triple-DES and similar
54    ciphers are SL_High.  ECC with 409 or more bits is also SL_High.
55    - Highest does not have an equivalent strength. It
56    indicates that the provider should use the strongest
57    ciphers available (but not less than SL_High).
58  */
59 enum SecurityLevel
60 {
61     SL_None,      ///< indicates that no security is ok
62     SL_Integrity, ///< must at least get integrity protection
63     SL_Export,    ///< must be export level bits or more
64     SL_Baseline,  ///< must be 128 bit or more
65     SL_High,      ///< must be more than 128 bit
66     SL_Highest    ///< SL_High or max possible, whichever is greater
67 };
68 
69 /**
70    \class SecureLayer qca_securelayer.h QtCrypto
71 
72    Abstract interface to a security layer
73 
74    SecureLayer is normally used between an application and a
75    potentially insecure network. It provides secure
76    communications over that network.
77 
78    The concept is that (after some initial setup), the
79    application can write() some data to the SecureLayer
80    implementation, and that data is encrypted (or otherwise
81    protected, depending on the setup). The SecureLayer
82    implementation then emits the readyReadOutgoing() signal,
83    and the application uses readOutgoing() to retrieve the
84    encrypted data from the SecureLayer implementation.  The
85    encrypted data is then sent out on the network.
86 
87    When some encrypted data comes back from the network, the
88    application does a writeIncoming() to the SecureLayer
89    implementation. Some time later, the SecureLayer
90    implementation may emit readyRead() to the application,
91    which then read()s the decrypted data from the SecureLayer
92    implementation.
93 
94    Note that sometimes data is sent or received between the
95    SecureLayer implementation and the network without any data
96    being sent between the application and the SecureLayer
97    implementation. This is a result of the initial negotiation
98    activities (which require network traffic to agree a
99    configuration to use) and other overheads associated with
100    the secure link.
101 
102    \ingroup UserAPI
103 */
104 class QCA_EXPORT SecureLayer : public QObject
105 {
106     Q_OBJECT
107 public:
108     /**
109        Constructor for an abstract secure communications
110        layer
111 
112        \param parent the parent object for this object
113     */
114     SecureLayer(QObject *parent = nullptr);
115 
116     /**
117        Returns true if the layer has a meaningful "close".
118     */
119     virtual bool isClosable() const;
120 
121     /**
122        Returns the number of bytes available to be read()
123        on the application side.
124     */
125     virtual int bytesAvailable() const = 0;
126 
127     /**
128        Returns the number of bytes available to be
129        readOutgoing() on the network side.
130     */
131     virtual int bytesOutgoingAvailable() const = 0;
132 
133     /**
134        Close the link. Note that this may not be
135        meaningful / possible for all implementations.
136 
137        \sa isClosable() for a test that verifies if the
138        link can be %closed.
139     */
140     virtual void close();
141 
142     /**
143        This method writes unencrypted (plain) data to
144        the SecureLayer implementation. You normally
145        call this function on the application side.
146 
147        \param a the source of the application-side data
148     */
149     virtual void write(const QByteArray &a) = 0;
150 
151     /**
152        This method reads decrypted (plain) data from
153        the SecureLayer implementation. You normally call
154        this function on the application side after receiving
155        the readyRead() signal.
156     */
157     virtual QByteArray read() = 0;
158 
159     /**
160        This method accepts encoded (typically encrypted) data
161        for processing. You normally call this function using
162        data read from the network socket (e.g. using
163        QTcpSocket::readAll()) after receiving a signal that
164        indicates that the socket has data to read.
165 
166        \param a the ByteArray to take network-side data from
167     */
168     virtual void writeIncoming(const QByteArray &a) = 0;
169 
170     /**
171        This method provides encoded (typically encrypted)
172        data. You normally call this function to get data
173        to write out to the network socket (e.g. using
174        QTcpSocket::write()) after receiving the
175        readyReadOutgoing() signal.
176 
177        \param plainBytes the number of bytes that were read.
178     */
179     virtual QByteArray readOutgoing(int *plainBytes = nullptr) = 0;
180 
181     /**
182        This allows you to read data without having it
183        decrypted first. This is intended to be used for
184        protocols that close off the connection and return
185        to plain text transfer. You do not normally need to
186        use this function.
187     */
188     virtual QByteArray readUnprocessed();
189 
190     /**
191        Convert encrypted bytes written to plain text bytes written
192 
193        \param encryptedBytes the number of bytes to convert
194     */
195     virtual int convertBytesWritten(qint64 encryptedBytes) = 0;
196 
197 Q_SIGNALS:
198     /**
199        This signal is emitted when SecureLayer has
200        decrypted (application side) data ready to be
201        read. Typically you will connect this signal to a
202        slot that reads the data (using read()).
203     */
204     void readyRead();
205 
206     /**
207        This signal is emitted when SecureLayer has encrypted
208        (network side) data ready to be read. Typically you
209        will connect this signal to a slot that reads the data
210        (using readOutgoing()) and writes it to a network socket.
211     */
212     void readyReadOutgoing();
213 
214     /**
215        This signal is emitted when the SecureLayer connection
216        is %closed.
217     */
218     void closed();
219 
220     /**
221        This signal is emitted when an error is detected. You
222        can determine the error type using errorCode().
223     */
224     void error();
225 
226 private:
227     Q_DISABLE_COPY(SecureLayer)
228 };
229 
230 /**
231    \class TLSSession qca_securelayer.h QtCrypto
232 
233    Session token, used for TLS resuming
234 
235    \ingroup UserAPI
236 
237 */
238 class QCA_EXPORT TLSSession : public Algorithm
239 {
240 public:
241     TLSSession();
242 
243     /**
244        Copy constructor
245 
246        \param from the session token to copy from
247     */
248     TLSSession(const TLSSession &from);
249 
250     ~TLSSession() override;
251 
252     /**
253        Assignment operator
254 
255        \param from the session token to assign from
256     */
257     TLSSession &operator=(const TLSSession &from);
258 
259     /**
260        Test if the session token is valid
261     */
262     bool isNull() const;
263 };
264 
265 /**
266    \class TLS qca_securelayer.h QtCrypto
267 
268    Transport Layer Security / Secure Socket Layer
269 
270    Transport Layer Security (%TLS) is the current
271    state-of-the-art in secure transport mechanisms over the
272    internet. It can be used in a way where only one side of
273    the link needs to authenticate to the other. This makes it
274    very useful for servers to provide their identity to
275    clients. Note that is is possible to use %TLS to
276    authenticate both client and server.
277 
278    %TLS is a IETF standard (<a
279    href="http://www.ietf.org/rfc/rfc2712.txt">RFC2712</a> for
280    TLS version 1.0, and <a
281    href="http://www.ietf.org/rfc/rfc4346.txt">RFC4346</a> for
282    TLS version 1.1) based on earlier Netscape work on Secure
283    Socket Layer (SSL version 2 and SSL version 3). New
284    applications should use at least TLS 1.0, and SSL version 2
285    should be avoided due to known security problems.
286 
287    \ingroup UserAPI
288 */
289 class QCA_EXPORT TLS : public SecureLayer, public Algorithm
290 {
291     Q_OBJECT
292 public:
293     /**
294        Operating mode
295     */
296     enum Mode
297     {
298         Stream,  ///< stream mode
299         Datagram ///< datagram mode
300     };
301 
302     /**
303        Version of %TLS or SSL
304     */
305     enum Version
306     {
307         TLS_v1, ///< Transport Layer Security, version 1
308         SSL_v3, ///< Secure Socket Layer, version 3
309         SSL_v2, ///< Secure Socket Layer, version 2
310         DTLS_v1 ///< Datagram Transport Layer Security, version 1
311     };
312 
313     /**
314        Type of error
315     */
316     enum Error
317     {
318         ErrorSignerExpired,   ///< local certificate is expired
319         ErrorSignerInvalid,   ///< local certificate is invalid in some way
320         ErrorCertKeyMismatch, ///< certificate and private key don't match
321         ErrorInit,            ///< problem starting up %TLS
322         ErrorHandshake,       ///< problem during the negotiation
323         ErrorCrypt            ///< problem at anytime after
324     };
325 
326     /**
327        Type of identity
328     */
329     enum IdentityResult
330     {
331         Valid,              ///< identity is verified
332         HostMismatch,       ///< valid cert provided, but wrong owner
333         InvalidCertificate, ///< invalid cert
334         NoCertificate       ///< identity unknown
335     };
336 
337     /**
338         Constructor for Transport Layer Security connection
339 
340         This produces a Stream (normal %TLS) rather than Datagram (DTLS)
341         object.
342         If you want to do DTLS, see below.
343 
344         \param parent the parent object for this object
345         \param provider the name of the provider, if a specific provider
346         is required
347     */
348     explicit TLS(QObject *parent = nullptr, const QString &provider = QString());
349 
350     /**
351        Constructor for Transport Layer Security connection.
352 
353        This constructor can be used for both normal %TLS (set mode to TLS::Stream)
354        or DTLS (set mode to TLS::Datagram).
355 
356        \param mode the connection Mode
357        \param parent the parent object for this object
358        \param provider the name of the provider, if a specific provider is
359        required
360     */
361     explicit TLS(Mode mode, QObject *parent = nullptr, const QString &provider = QString());
362 
363     /**
364        Destructor
365     */
366     ~TLS() override;
367 
368     /**
369        Reset the connection
370     */
371     void reset();
372 
373     /**
374        Get the list of cipher suites that are available for use.
375 
376        A cipher suite is a combination of key exchange,
377        encryption and hashing algorithms that are agreed
378        during the initial handshake between client and
379        server.
380 
381        \param version the protocol Version that the cipher
382        suites are required for
383 
384        \return list of the names of the cipher suites
385        supported.
386     */
387     QStringList supportedCipherSuites(const Version &version = TLS_v1) const;
388 
389     /**
390        The local certificate to use. This is the
391        certificate that will be provided to the peer. This
392        is almost always required on the server side
393        (because the server has to provide a certificate to
394        the client), and may be used on the client side.
395 
396        \param cert a chain of certificates that
397        link the host certificate to a trusted root
398        certificate.
399        \param key the private key for the certificate
400        chain
401     */
402     void setCertificate(const CertificateChain &cert, const PrivateKey &key);
403 
404     /**
405        \overload
406 
407        Allows setting a certificate from a KeyBundle.
408 
409        \param kb key bundle containing the local certificate
410        and associated private key.
411     */
412     void setCertificate(const KeyBundle &kb);
413 
414     /**
415        Return the trusted certificates set for this object
416     */
417     CertificateCollection trustedCertificates() const;
418 
419     /**
420        Set up the set of trusted certificates that will be used to verify
421        that the certificate provided is valid.
422 
423        Typically, this will be the collection of root certificates from
424        the system, which you can get using QCA::systemStore(), however you
425        may choose to pass whatever certificates match your assurance
426        needs.
427 
428        \param trusted a bundle of trusted certificates.
429     */
430     void setTrustedCertificates(const CertificateCollection &trusted);
431 
432     /**
433        The security level required for this link
434 
435        \param s the level required for this link.
436     */
437     void setConstraints(SecurityLevel s);
438 
439     /**
440        \overload
441 
442        \param minSSF the minimum Security Strength Factor
443        required for this link.
444        \param maxSSF the maximum Security Strength Factor
445        required for this link.
446     */
447     void setConstraints(int minSSF, int maxSSF);
448 
449     /**
450        \overload
451 
452        \param cipherSuiteList a list of the names of
453        cipher suites that can be used for this link.
454 
455        \note the names are the same as the names in the
456        applicable IETF RFCs (or Internet Drafts if there
457        is no applicable RFC).
458     */
459     void setConstraints(const QStringList &cipherSuiteList);
460 
461     /**
462        Retrieve the list of allowed issuers by the server,
463        if the server has provided them.  Only DN types will
464        be present.
465 
466        \code
467 Certificate someCert = ...
468 PrivateKey someKey = ...
469 
470 // see if the server will take our cert
471 CertificateInfoOrdered issuerInfo = someCert.issuerInfoOrdered().dnOnly();
472 foreach(const CertificateInfoOrdered &info, tls->issuerList())
473 {
474     if(info == issuerInfo)
475     {
476         // server will accept someCert, let's present it
477         tls->setCertificate(someCert, someKey);
478         break;
479     }
480 }
481        \endcode
482     */
483     QList<CertificateInfoOrdered> issuerList() const;
484 
485     /**
486        Sets the issuer list to present to the client.  For
487        use with servers only.  Only DN types are allowed.
488 
489        \param issuers the list of valid issuers to be used.
490     */
491     void setIssuerList(const QList<CertificateInfoOrdered> &issuers);
492 
493     /**
494        Resume a %TLS session using the given session object
495 
496        \param session the session state to use for resumption.
497     */
498     void setSession(const TLSSession &session);
499 
500     /**
501        Test if the link can use compression
502 
503        \return true if the link can use compression
504     */
505     bool canCompress() const;
506 
507     /**
508        Test if the link can specify a hostname (Server Name
509        Indication)
510 
511        \return true if the link can specify a hostname
512     */
513     bool canSetHostName() const;
514 
515     /**
516        Returns true if compression is enabled
517 
518        This only indicates whether or not the object is configured to use
519        compression, not whether or not the link is actually compressed.
520        Use isCompressed() for that.
521     */
522     bool compressionEnabled() const;
523 
524     /**
525        Set the link to use compression
526 
527        \param b true if the link should use compression, or false to
528        disable compression
529     */
530     void setCompressionEnabled(bool b);
531 
532     /**
533        Returns the host name specified or an empty string if no host
534        name is specified.
535     */
536     QString hostName() const;
537 
538     /**
539        Start the %TLS/SSL connection as a client
540 
541        Typically, you'll want to perform RFC 2818 validation on the
542        server's certificate, based on the hostname you're intending
543        to connect to.  Pass a value for \a host in order to have the
544        validation for you.  If you want to bypass this behavior and
545        do the validation yourself, pass an empty string for \a host.
546 
547        If the host is an internationalized domain name, then it must be
548        provided in unicode format, not in IDNA ACE/punycode format.
549 
550        \param host the hostname that you want to connect to
551 
552        \note The hostname will be used for Server Name Indication
553        extension (see
554        <a href="http://www.ietf.org/rfc/rfc3546.txt">RFC 3546</a> Section
555        3.1) if supported by the backend provider.
556     */
557     void startClient(const QString &host = QString());
558 
559     /**
560        Start the %TLS/SSL connection as a server.
561     */
562     void startServer();
563 
564     /**
565        Resumes %TLS processing.
566 
567        Call this function after hostNameReceived(), certificateRequested()
568        peerCertificateAvailable() or handshaken() is emitted.  By
569        requiring this function to be called in order to proceed,
570        applications are given a chance to perform user interaction between
571        steps in the %TLS process.
572     */
573     void continueAfterStep();
574 
575     /**
576        test if the handshake is complete
577 
578        \return true if the handshake is complete
579 
580        \sa handshaken
581     */
582     bool isHandshaken() const;
583 
584     /**
585        test if the link is compressed
586 
587        \return true if the link is compressed
588     */
589     bool isCompressed() const;
590 
591     /**
592        The protocol version that is in use for this connection.
593     */
594     Version version() const;
595 
596     /**
597        The cipher suite that has been negotiated for this connection.
598 
599        The name returned here is the name used in the applicable RFC
600        (or Internet Draft, where there is no RFC).
601     */
602     QString cipherSuite() const;
603 
604     /**
605        The number of effective bits of security being used for this
606        connection.
607 
608        This can differ from the actual number of bits in
609        the cipher for certain
610        older "export ciphers" that are deliberately crippled. If you
611        want that information, use cipherMaxBits().
612     */
613     int cipherBits() const;
614 
615     /**
616        The number of bits of security that the cipher could use.
617 
618        This is normally the same as cipherBits(), but can be greater
619        for older "export ciphers".
620     */
621     int cipherMaxBits() const;
622 
623     /**
624        The session object of the %TLS connection, which can be used
625        for resuming.
626     */
627     TLSSession session() const;
628 
629     /**
630        This method returns the type of error that has
631        occurred. You should only need to check this if the
632        error() signal is emitted.
633     */
634     Error errorCode() const;
635 
636     /**
637        After the SSL/%TLS handshake is complete, this
638        method allows you to determine if the other end
639        of the connection (if the application is a client,
640        this is the server; if the application is a server,
641        this is the client) has a valid identity.
642 
643        Note that the security of %TLS/SSL depends on
644        checking this. It is not enough to check that the
645        certificate is valid - you must check that the
646        certificate is valid for the entity that you are
647        trying to communicate with.
648 
649        \note If this returns QCA::TLS::InvalidCertificate,
650        you may wish to use peerCertificateValidity() to
651        determine whether to proceed or not.
652     */
653     IdentityResult peerIdentityResult() const;
654 
655     /**
656        After the SSL/%TLS handshake is valid, this method
657        allows you to check if the received certificate
658        from the other end is valid. As noted in
659        peerIdentityResult(), you also need to check that
660        the certificate matches the entity you are trying
661        to communicate with.
662     */
663     Validity peerCertificateValidity() const;
664 
665     /**
666        The CertificateChain for the local host
667        certificate.
668     */
669     CertificateChain localCertificateChain() const;
670 
671     /**
672        The PrivateKey for the local host
673        certificate.
674     */
675     PrivateKey localPrivateKey() const;
676 
677     /**
678        The CertificateChain from the peer (other end of
679        the connection to the trusted root certificate).
680     */
681     CertificateChain peerCertificateChain() const;
682 
683     // reimplemented
684     bool       isClosable() const override;
685     int        bytesAvailable() const override;
686     int        bytesOutgoingAvailable() const override;
687     void       close() override;
688     void       write(const QByteArray &a) override;
689     QByteArray read() override;
690     void       writeIncoming(const QByteArray &a) override;
691     QByteArray readOutgoing(int *plainBytes = nullptr) override;
692     QByteArray readUnprocessed() override;
693     int        convertBytesWritten(qint64 encryptedBytes) override;
694 
695     /**
696        Determine the number of packets available to be
697        read on the application side.
698 
699        \note this is only used with DTLS.
700     */
701     int packetsAvailable() const;
702 
703     /**
704        Determine the number of packets available to be
705        read on the network side.
706 
707        \note this is only used with DTLS.
708     */
709     int packetsOutgoingAvailable() const;
710 
711     /**
712        Return the currently configured maximum packet size
713 
714        \note this is only used with DTLS
715     */
716     int packetMTU() const;
717 
718     /**
719        Set the maximum packet size to use.
720 
721        \param size the number of bytes to set as the MTU.
722 
723        \note this is only used with DTLS.
724     */
725     void setPacketMTU(int size) const;
726 
727 Q_SIGNALS:
728     /**
729        Emitted if a host name is set by the client.  At
730        this time, the server can inspect the hostName().
731 
732        You must call continueAfterStep() in order for %TLS
733        processing to resume after this signal is emitted.
734 
735        This signal is only emitted in server mode.
736 
737        \sa continueAfterStep
738     */
739     void hostNameReceived();
740 
741     /**
742        Emitted when the server requests a certificate.  At
743        this time, the client can inspect the issuerList().
744 
745        You must call continueAfterStep() in order for %TLS
746        processing to resume after this signal is emitted.
747 
748        This signal is only emitted in client mode.
749 
750        \sa continueAfterStep
751     */
752     void certificateRequested();
753 
754     /**
755        Emitted when a certificate is received from the peer.
756        At this time, you may inspect peerIdentityResult(),
757        peerCertificateValidity(), and peerCertificateChain().
758 
759        You must call continueAfterStep() in order for %TLS
760        processing to resume after this signal is emitted.
761 
762        \sa continueAfterStep
763     */
764     void peerCertificateAvailable();
765 
766     /**
767        Emitted when the protocol handshake is complete.  At
768        this time, all available information about the %TLS
769        session can be inspected.
770 
771        You must call continueAfterStep() in order for %TLS
772        processing to resume after this signal is emitted.
773 
774        \sa continueAfterStep
775        \sa isHandshaken
776     */
777     void handshaken();
778 
779 protected:
780     /**
781        Called when a connection is made to a particular signal
782 
783        \param signal the name of the signal that has been
784        connected to.
785     */
786     void connectNotify(const QMetaMethod &signal) override;
787 
788     /**
789        Called when a connection is removed from a particular signal
790 
791        \param signal the name of the signal that has been
792        disconnected from.
793     */
794     void disconnectNotify(const QMetaMethod &signal) override;
795 
796 private:
797     Q_DISABLE_COPY(TLS)
798 
799     class Private;
800     friend class Private;
801     Private *d;
802 };
803 
804 /**
805    \class SASL qca_securelayer.h QtCrypto
806 
807    Simple Authentication and Security Layer protocol implementation
808 
809    This class implements the Simple Authenication and Security Layer protocol,
810    which is described in RFC2222 - see
811    <a href="http://www.ietf.org/rfc/rfc2222.txt">http://www.ietf.org/rfc/rfc2222.txt</a>.
812 
813    As the name suggests, %SASL provides authentication (eg, a "login" of some
814    form), for a connection oriented protocol, and can also provide protection
815    for the subsequent connection.
816 
817    The %SASL protocol is designed to be extensible, through a range of
818    "mechanisms", where a mechanism is the actual authentication method.
819    Example mechanisms include Anonymous, LOGIN, Kerberos V4, and GSSAPI.
820    Mechanisms can be added (potentially without restarting the server
821    application) by the system administrator.
822 
823    It is important to understand that %SASL is neither "network aware" nor
824    "protocol aware".  That means that %SASL does not understand how the client
825    connects to the server, and %SASL does not understand the actual
826    application protocol.
827 
828    \ingroup UserAPI
829 
830 */
831 class QCA_EXPORT SASL : public SecureLayer, public Algorithm
832 {
833     Q_OBJECT
834 public:
835     /**
836        Possible errors that may occur when using %SASL
837     */
838     enum Error
839     {
840         ErrorInit,      ///< problem starting up %SASL
841         ErrorHandshake, ///< problem during the authentication process
842         ErrorCrypt      ///< problem at anytime after
843     };
844 
845     /**
846        Possible authentication error states
847     */
848     enum AuthCondition
849     {
850         AuthFail,         ///< Generic authentication failure
851         NoMechanism,      ///< No compatible/appropriate authentication mechanism
852         BadProtocol,      ///< Bad protocol or cancelled
853         BadServer,        ///< Server failed mutual authentication (client side only)
854         BadAuth,          ///< Authentication failure (server side only)
855         NoAuthzid,        ///< Authorization failure (server side only)
856         TooWeak,          ///< Mechanism too weak for this user (server side only)
857         NeedEncrypt,      ///< Encryption is needed in order to use mechanism (server side only)
858         Expired,          ///< Passphrase expired, has to be reset (server side only)
859         Disabled,         ///< Account is disabled (server side only)
860         NoUser,           ///< User not found (server side only)
861         RemoteUnavailable ///< Remote service needed for auth is gone (server side only)
862     };
863 
864     /**
865        Authentication requirement flag values
866     */
867     enum AuthFlags
868     {
869         AuthFlagsNone          = 0x00,
870         AllowPlain             = 0x01,
871         AllowAnonymous         = 0x02,
872         RequireForwardSecrecy  = 0x04,
873         RequirePassCredentials = 0x08,
874         RequireMutualAuth      = 0x10,
875         RequireAuthzidSupport  = 0x20 // server-only
876     };
877 
878     /**
879        Mode options for client side sending
880     */
881     enum ClientSendMode
882     {
883         AllowClientSendFirst,
884         DisableClientSendFirst
885     };
886 
887     /**
888        Mode options for server side sending
889     */
890     enum ServerSendMode
891     {
892         AllowServerSendLast,
893         DisableServerSendLast
894     };
895 
896     /**
897        \class Params qca_securelayer.h QtCrypto
898 
899        Parameter flags for the %SASL authentication
900 
901        This is used to indicate which parameters are needed by %SASL
902        in order to complete the authentication process.
903 
904        \ingroup UserAPI
905     */
906     class QCA_EXPORT Params
907     {
908     public:
909         Params();
910 
911         /**
912            Standard constructor.
913 
914            The concept behind this is that you set each of the
915            flags depending on which parameters are needed.
916 
917            \param user the username is required
918            \param authzid the authorization identity is required
919            \param pass the password is required
920            \param realm the realm is required
921         */
922         Params(bool user, bool authzid, bool pass, bool realm);
923 
924         /**
925            Standard copy constructor
926 
927            \param from the Params object to copy
928         */
929         Params(const Params &from);
930         ~Params();
931 
932         /**
933            Standard assignment operator
934 
935            \param from the Params object to assign from
936         */
937         Params &operator=(const Params &from);
938 
939         /**
940            User is needed
941         */
942         bool needUsername() const;
943 
944         /**
945            An Authorization ID can be sent if desired
946         */
947         bool canSendAuthzid() const;
948 
949         /**
950            Password is needed
951         */
952         bool needPassword() const;
953 
954         /**
955            A Realm can be sent if desired
956         */
957         bool canSendRealm() const;
958 
959     private:
960         class Private;
961         Private *d;
962     };
963 
964     /**
965        Standard constructor
966 
967        \param parent the parent object for this %SASL connection
968        \param provider if specified, the provider to use. If not
969        specified, or specified as empty, then any provider is
970        acceptable.
971     */
972     explicit SASL(QObject *parent = nullptr, const QString &provider = QString());
973 
974     ~SASL() override;
975 
976     /**
977        Reset the %SASL mechanism
978     */
979     void reset();
980 
981     /**
982        Specify connection constraints
983 
984        %SASL supports a range of authentication requirements, and
985        a range of security levels. This method allows you to
986        specify the requirements for your connection.
987 
988        \param f the authentication requirements, which you typically
989        build using a binary OR function (eg AllowPlain | AllowAnonymous)
990        \param s the security level of the encryption, if used. See
991        SecurityLevel for details of what each level provides.
992     */
993     void setConstraints(AuthFlags f, SecurityLevel s = SL_None);
994 
995     /**
996        \overload
997 
998        Unless you have a specific reason for directly specifying a
999        strength factor, you probably should use the method above.
1000 
1001        \param f the authentication requirements, which you typically
1002        build using a binary OR function (eg AllowPlain | AllowAnonymous)
1003        \param minSSF the minimum security strength factor that is required
1004        \param maxSSF the maximum security strength factor that is required
1005 
1006        \note Security strength factors are a rough approximation to key
1007        length in the encryption function (eg if you are securing with
1008        plain DES, the security strength factor would be 56).
1009     */
1010     void setConstraints(AuthFlags f, int minSSF, int maxSSF);
1011 
1012     /**
1013        Specify the local address.
1014 
1015        \param addr the address of the local part of the connection
1016        \param port the port number of the local part of the connection
1017     */
1018     void setLocalAddress(const QString &addr, quint16 port);
1019 
1020     /**
1021        Specify the peer address.
1022 
1023        \param addr the address of the peer side of the connection
1024        \param port the port number of the peer side of the connection
1025     */
1026     void setRemoteAddress(const QString &addr, quint16 port);
1027 
1028     /**
1029        Specify the id of the externally secured connection
1030 
1031        \param authid the id of the connection
1032     */
1033     void setExternalAuthId(const QString &authid);
1034 
1035     /**
1036        Specify a security strength factor for an externally secured
1037        connection
1038 
1039        \param strength the security strength factor of the connection
1040     */
1041     void setExternalSSF(int strength);
1042 
1043     /**
1044        Initialise the client side of the connection
1045 
1046        startClient must be called on the client side of the connection.
1047        clientStarted will be emitted when the operation is completed.
1048 
1049        \param service the name of the service
1050        \param host the client side host name
1051        \param mechlist the list of mechanisms which can be used
1052        \param mode the mode to use on the client side
1053     */
1054     void startClient(const QString &    service,
1055                      const QString &    host,
1056                      const QStringList &mechlist,
1057                      ClientSendMode     mode = AllowClientSendFirst);
1058 
1059     /**
1060        Initialise the server side of the connection
1061 
1062        startServer must be called on the server side of the connection.
1063        serverStarted will be emitted when the operation is completed.
1064 
1065        \param service the name of the service
1066        \param host the server side host name
1067        \param realm the realm to use
1068        \param mode which mode to use on the server side
1069     */
1070     void startServer(const QString &service,
1071                      const QString &host,
1072                      const QString &realm,
1073                      ServerSendMode mode = DisableServerSendLast);
1074 
1075     /**
1076        Process the first step in server mode (server)
1077 
1078        Call this with the mechanism selected by the client.  If there
1079        is initial client data, call the other version of this function
1080        instead.
1081 
1082        \param mech the mechanism to be used.
1083     */
1084     void putServerFirstStep(const QString &mech);
1085 
1086     /**
1087        Process the first step in server mode (server)
1088 
1089        Call this with the mechanism selected by the client, and initial
1090        client data.  If there is no initial client data, call the other
1091        version of this function instead.
1092 
1093        \param mech the mechanism to be used
1094        \param clientInit the initial data provided by the client side
1095     */
1096     void putServerFirstStep(const QString &mech, const QByteArray &clientInit);
1097 
1098     /**
1099        Process an authentication step
1100 
1101        Call this with authentication data received from the network.
1102        The only exception is the first step in server mode, in which
1103        case putServerFirstStep must be called.
1104 
1105        \param stepData the authentication data from the network
1106     */
1107     void putStep(const QByteArray &stepData);
1108 
1109     /**
1110        Return the mechanism selected (client)
1111     */
1112     QString mechanism() const;
1113 
1114     /**
1115        Return the mechanism list (server)
1116     */
1117     QStringList mechanismList() const;
1118 
1119     /**
1120        Return the realm list, if available (client)
1121     */
1122     QStringList realmList() const;
1123 
1124     /**
1125        Return the security strength factor of the connection
1126     */
1127     int ssf() const;
1128 
1129     /**
1130        Return the error code
1131     */
1132     Error errorCode() const;
1133 
1134     /**
1135        Return the reason for authentication failure
1136     */
1137     AuthCondition authCondition() const;
1138 
1139     /**
1140        Specify the username to use in authentication
1141 
1142        \param user the username to use
1143     */
1144     void setUsername(const QString &user);
1145 
1146     /**
1147        Specify the authorization identity to use in authentication
1148 
1149        \param auth the authorization identity to use
1150     */
1151     void setAuthzid(const QString &auth);
1152 
1153     /**
1154        Specify the password to use in authentication
1155 
1156        \param pass the password to use
1157     */
1158     void setPassword(const SecureArray &pass);
1159 
1160     /**
1161        Specify the realm to use in authentication
1162 
1163        \param realm the realm to use
1164     */
1165     void setRealm(const QString &realm);
1166 
1167     /**
1168        Continue negotiation after parameters have been set (client)
1169     */
1170     void continueAfterParams();
1171 
1172     /**
1173        Continue negotiation after auth ids have been checked (server)
1174     */
1175     void continueAfterAuthCheck();
1176 
1177     // reimplemented
1178     int        bytesAvailable() const override;
1179     int        bytesOutgoingAvailable() const override;
1180     void       write(const QByteArray &a) override;
1181     QByteArray read() override;
1182     void       writeIncoming(const QByteArray &a) override;
1183     QByteArray readOutgoing(int *plainBytes = nullptr) override;
1184     int        convertBytesWritten(qint64 encryptedBytes) override;
1185 
1186 Q_SIGNALS:
1187     /**
1188        This signal is emitted when the client has been successfully
1189        started
1190 
1191        \param clientInit true if the client should send an initial
1192        response to the server
1193        \param clientInitData the initial response to send to the server.
1194        Do note that there is a difference in SASL between an empty initial
1195        response and no initial response, and so even if clientInitData is
1196        an empty array, you still need to send an initial response if
1197        clientInit is true.
1198     */
1199     void clientStarted(bool clientInit, const QByteArray &clientInitData);
1200 
1201     /**
1202        This signal is emitted after the server has been
1203        successfully started
1204     */
1205     void serverStarted();
1206 
1207     /**
1208        This signal is emitted when there is data required
1209        to be sent over the network to complete the next
1210        step in the authentication process.
1211 
1212        \param stepData the data to send over the network
1213     */
1214     void nextStep(const QByteArray &stepData);
1215 
1216     /**
1217        This signal is emitted when the client needs
1218        additional parameters
1219 
1220        After receiving this signal, the application should set
1221        the required parameter values appropriately and then call
1222        continueAfterParams().
1223 
1224        \param params the parameters that are required by the client
1225     */
1226     void needParams(const QCA::SASL::Params &params);
1227 
1228     /**
1229        This signal is emitted when the server needs to
1230        perform the authentication check
1231 
1232        If the user and authzid are valid, call continueAfterAuthCheck().
1233 
1234        \param user the user identification name
1235        \param authzid the user authorization name
1236     */
1237     void authCheck(const QString &user, const QString &authzid);
1238 
1239     /**
1240        This signal is emitted when authentication is complete.
1241     */
1242     void authenticated();
1243 
1244 private:
1245     Q_DISABLE_COPY(SASL)
1246 
1247     class Private;
1248     friend class Private;
1249     Private *d;
1250 };
1251 
1252 }
1253 
1254 #endif
1255