File indexing completed on 2024-04-28 04:43:41

0001 /*
0002  * qca_support.h - Qt Cryptographic Architecture
0003  * Copyright (C) 2003-2005  Justin Karneges <justin@affinix.com>
0004  * Copyright (C) 2004,2005, 2007  Brad Hards <bradh@frogmouth.net>
0005  *
0006  * This library is free software; you can redistribute it and/or
0007  * modify it under the terms of the GNU Lesser General Public
0008  * License as published by the Free Software Foundation; either
0009  * version 2.1 of the License, or (at your option) any later version.
0010  *
0011  * This library is distributed in the hope that it will be useful,
0012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
0013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0014  * Lesser General Public License for more details.
0015  *
0016  * You should have received a copy of the GNU Lesser General Public
0017  * License along with this library; if not, write to the Free Software
0018  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
0019  * 02110-1301  USA
0020  *
0021  */
0022 
0023 /**
0024    \file qca_support.h
0025 
0026    Header file for "support" classes used in %QCA
0027 
0028    The classes in this header do not have any cryptographic
0029    content - they are used in %QCA, and are included for convenience.
0030 
0031    \note You should not use this header directly from an
0032    application. You should just use <tt> \#include \<QtCrypto>
0033    </tt> instead.
0034 */
0035 
0036 #ifndef QCA_SUPPORT_H
0037 #define QCA_SUPPORT_H
0038 
0039 #include "qca_export.h"
0040 #include "qca_tools.h"
0041 #include <QByteArray>
0042 #include <QList>
0043 #include <QMetaObject>
0044 #include <QObject>
0045 #include <QString>
0046 #include <QStringList>
0047 #include <QThread>
0048 #include <QVariant>
0049 #include <QVariantList>
0050 
0051 namespace QCA {
0052 
0053 /**
0054    Convenience method to determine the return type of a method
0055 
0056    This function identifies the return type of a specified
0057    method. This function can be used as shown:
0058    \code
0059 class TestClass : public QObject
0060 {
0061     Q_OBJECT
0062     // ...
0063 public slots:
0064     QString qstringMethod()  { return QString(); };
0065     bool boolMethod( const QString & )  { return true; };
0066 };
0067 
0068 QByteArray myTypeName;
0069 
0070 TestClass testClass;
0071 QList<QByteArray> argsList; // empty list, since no args
0072 
0073 myTypeName = QCA::methodReturnType( testClass.metaObject(), QByteArray( "qstringMethod" ), argsList );
0074 // myTypeName is "QString"
0075 
0076 myTypeName = QCA::methodReturnType( testClass.metaObject(), QByteArray( "boolMethod" ), argsList );
0077 // myTypeName is "", because there is no method called "boolMethod" that has no arguments
0078 
0079 argsList << "QString"; // now we have one argument
0080 myTypeName = QCA::methodReturnType( testClass.metaObject(), QByteArray( "boolMethod" ), argsList );
0081 // myTypeName is "bool"
0082    \endcode
0083 
0084    The return type name of a method returning void is an empty string, not "void"
0085 
0086    \note This function is not normally required for use with
0087    %QCA. It is provided for use in your code, if required.
0088 
0089    \param obj the QMetaObject for the object
0090    \param method the name of the method (without the arguments or brackets)
0091    \param argTypes the list of argument types of the method
0092 
0093    \return the name of the type that this method will return with the specified
0094    argument types.
0095 
0096    \sa QMetaType for more information on the Qt meta type system.
0097 
0098    \relates SyncThread
0099 */
0100 
0101 #if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0)
0102 QCA_EXPORT int methodReturnType(const QMetaObject *obj, const QByteArray &method, const QList<QByteArray> &argTypes);
0103 #else
0104 QCA_EXPORT QByteArray methodReturnType(const QMetaObject      *obj,
0105                                        const QByteArray       &method,
0106                                        const QList<QByteArray> argTypes);
0107 #endif
0108 
0109 /**
0110    Convenience method to invoke a method by name, using a variant
0111    list of arguments.
0112 
0113    This function can be used as shown:
0114    \code
0115 class TestClass : public QObject
0116 {
0117     Q_OBJECT
0118     // ...
0119 public slots:
0120     QString qstringMethod()  { return QString( "the result" ); };
0121     bool boolMethod( const QString & )  { return true; };
0122 };
0123 
0124 TestClass *testClass = new TestClass;
0125 QVariantList args;
0126 
0127 QVariant stringRes;
0128 // calls testClass->qstringMethod() with no arguments ( since args is an empty list)
0129 bool ret = QCA::invokeMethodWithVariants( testClass, QByteArray( "qstringMethod" ), args, &stringRes );
0130 // ret is true (since call succeeded), stringRes.toString() is a string - "the result"
0131 
0132 QVariant boolResult;
0133 QString someString( "not important" );
0134 args << someString;
0135 // calls testClass->boolMethod( someString ), returning result in boolResult
0136 ret = QCA::invokeMethodWithVariants( testClass1, QByteArray( "boolMethod" ), args, &boolResult );
0137 // ret is true (since call succeeded), boolResult.toBool() is true.
0138    \endcode
0139 
0140    \param obj the object to call the method on
0141    \param method the name of the method (without the arguments or brackets)
0142    \param args the list of arguments to use in the method call
0143    \param ret the return value of the method (unchanged if the call fails)
0144    \param type the type of connection to use
0145 
0146    \return true if the call succeeded, otherwise false
0147 
0148    \relates SyncThread
0149 */
0150 QCA_EXPORT bool invokeMethodWithVariants(QObject            *obj,
0151                                          const QByteArray   &method,
0152                                          const QVariantList &args,
0153                                          QVariant           *ret,
0154                                          Qt::ConnectionType  type = Qt::AutoConnection);
0155 
0156 /**
0157    \class SyncThread qca_support.h QtCrypto
0158 
0159    Convenience class to run a thread and interact with it synchronously
0160 
0161    SyncThread makes it easy to perform the common practice of starting a
0162    thread, running some objects in that thread, and then interacting with
0163    those objects safely.  Often, there is no need to directly use threading
0164    primitives (e.g. QMutex), resulting in very clean multi-threaded code.
0165 
0166    \note The following is an excerpt from
0167    http://delta.affinix.com/2006/11/13/synchronized-threads-part-3/
0168 
0169    ---<br>
0170    With SyncThread, you can start, stop, and call a method in another thread
0171    while the main thread sleeps. The only requirement is that the methods be
0172    declared as slots.
0173 
0174    Below is a contrived example, where we have an object in another thread
0175    that increments a counter over a some interval, using the Qt event loop,
0176    and provides a method to inspect the value.
0177 
0178    First, the Counter object:
0179 
0180 \code
0181 class Counter : public QObject
0182 {
0183     Q_OBJECT
0184 private:
0185     int x;
0186     QTimer timer;
0187 
0188 public:
0189     Counter() : timer(this)
0190     {
0191         x = 0;
0192         connect(&timer, &QTimer::timeout, this, &Counter::t_timeout);
0193     }
0194 
0195 public slots:
0196     void start(int seconds)
0197     {
0198         timer.setInterval(seconds * 1000);
0199         timer.start();
0200     }
0201 
0202     int value() const
0203     {
0204         return x;
0205     }
0206 
0207 private Q_SLOTS:
0208     void t_timeout()
0209     {
0210         ++x;
0211     }
0212 };
0213 \endcode
0214 
0215    Looks like a typical object, no surprises.
0216 
0217    Now to wrap Counter with SyncThread. We went over how to do this in the
0218    first article, and it is very straightforward:
0219 
0220 \code
0221 class CounterThread : public SyncThread
0222 {
0223     Q_OBJECT
0224 public:
0225     Counter *counter;
0226 
0227     CounterThread(QObject *parent) : SyncThread(parent)
0228     {
0229         counter = 0;
0230     }
0231 
0232     ~CounterThread()
0233     {
0234         // SyncThread will stop the thread on destruct, but since our
0235         //   atStop() function makes references to CounterThread's
0236         //   members, we need to shutdown here, before CounterThread
0237         //   destructs.
0238         stop();
0239     }
0240 
0241 protected:
0242     virtual void atStart()
0243     {
0244         counter = new Counter;
0245     }
0246 
0247     virtual void atStop()
0248     {
0249         delete counter;
0250     }
0251 };
0252 \endcode
0253 
0254    We can then use it like this:
0255 
0256 \code
0257 CounterThread *thread = new CounterThread;
0258 
0259 // after this call, the thread is started and the Counter is ready
0260 thread->start();
0261 
0262 // let's start the counter with a 1 second interval
0263 thread->call(thread->counter, "start", QVariantList() << 1);
0264 ...
0265 
0266 // after some time passes, let's check on the value
0267 int x = thread->call(thread->counter, "value").toInt();
0268 
0269 // we're done with this thing
0270 delete thread;
0271 \endcode
0272 
0273    Even without the call() function, SyncThread is still very useful
0274    for preparing objects in another thread, which you can then
0275    QObject::connect() to and use signals and slots like normal.
0276 
0277    \ingroup UserAPI
0278 */
0279 class QCA_EXPORT SyncThread : public QThread
0280 {
0281     Q_OBJECT
0282 public:
0283     /**
0284        Standard constructor
0285 
0286        \param parent the parent object for this parent.
0287     */
0288     SyncThread(QObject *parent = nullptr);
0289 
0290     /**
0291        Calls stop() and then destructs
0292 
0293        \note Subclasses should call stop() in their own destructor
0294     */
0295     ~SyncThread() override;
0296 
0297     /**
0298        Starts the thread, begins the event loop the thread, and then
0299        calls atStart() in the thread.  This function will block until
0300        atStart() has returned.
0301     */
0302     void start();
0303 
0304     /**
0305        Stops the event loop of the thread, calls atStop() in the thread,
0306        and instructs the thread to finish.  This function will block
0307        until the thread has finished.
0308     */
0309     void stop();
0310 
0311     /**
0312        Calls a slot of an object in the thread.  This function will block
0313        until the slot has returned.
0314 
0315        It is possible for the call to fail, for example if the method
0316        does not exist.
0317 
0318        The arguments and return value of the call use QVariant.  If the
0319        method has no return value (returns void), then the returned
0320        QVariant will be null.
0321 
0322        \param obj the object to call the method on
0323        \param method the name of the method (without the arguments or
0324        brackets)
0325        \param args the list of arguments to use in the method call
0326        \param ok if not 0, true is stored here if the call succeeds,
0327        otherwise false is stored here.
0328     */
0329     QVariant
0330     call(QObject *obj, const QByteArray &method, const QVariantList &args = QVariantList(), bool *ok = nullptr);
0331 
0332 protected:
0333     /**
0334        Reimplement this to perform your initialization
0335     */
0336     virtual void atStart() = 0;
0337 
0338     /**
0339        Reimplement this to perform your deinitialization
0340     */
0341     virtual void atEnd() = 0;
0342 
0343     /**
0344        Starts the event loop and calls atStart and atStop as necessary
0345     */
0346     void run() override;
0347 
0348 private:
0349     Q_DISABLE_COPY(SyncThread)
0350 
0351     class Private;
0352     friend class Private;
0353     Private *d;
0354 };
0355 
0356 /**
0357   \class Synchronizer qca_support.h QtCrypto
0358 
0359   Enable synchronization between two threads.
0360 */
0361 class QCA_EXPORT Synchronizer : public QObject
0362 {
0363     Q_OBJECT
0364 public:
0365     /**
0366       Standard constructor
0367 
0368       \param parent the parent object to this object
0369     */
0370     Synchronizer(QObject *parent);
0371     ~Synchronizer() override;
0372 
0373     /**
0374        Call to pause execution in this thread. This function
0375        will block until conditionMet() is called.
0376 
0377        \param msecs the time to wait before proceeding. The default
0378        timeout value (-1) indicates to wait indefinitely.
0379     */
0380     bool waitForCondition(int msecs = -1);
0381 
0382     /**
0383        Call to continue execution in the paused thread.
0384     */
0385     void conditionMet();
0386 
0387 private:
0388     Q_DISABLE_COPY(Synchronizer)
0389 
0390     class Private;
0391     Private *d;
0392 };
0393 
0394 /**
0395    \class DirWatch qca_support.h QtCrypto
0396 
0397    Support class to monitor a directory for activity.
0398 
0399    %DirWatch monitors a specified file for any changes. When
0400    the directory changes, the changed() signal is emitted.
0401 
0402    \note QFileSystemWatcher has very similar functionality
0403    to this class. You should evaluate this class and
0404    QFileSystemWatcher to determine which better suits your
0405    application needs.
0406 
0407    \ingroup UserAPI
0408 */
0409 class QCA_EXPORT DirWatch : public QObject
0410 {
0411     Q_OBJECT
0412 public:
0413     /**
0414        Standard constructor
0415 
0416        \param dir the name of the directory to watch. If not
0417        set in the constructor, you can set it using setDirName()
0418        \param parent the parent object for this object
0419     */
0420     explicit DirWatch(const QString &dir = QString(), QObject *parent = nullptr);
0421     ~DirWatch() override;
0422 
0423     /**
0424        The name of the directory that is being monitored
0425     */
0426     QString dirName() const;
0427 
0428     /**
0429        Change the directory being monitored
0430 
0431        \param dir the name of the directory to monitor
0432     */
0433     void setDirName(const QString &dir);
0434 
0435 Q_SIGNALS:
0436     /**
0437        The changed signal is emitted when the directory is
0438        changed (e.g.\ modified by addition or deletion of a
0439        file within the directory, or the deletion of the
0440        directory)
0441     */
0442     void changed();
0443 
0444 private:
0445     Q_DISABLE_COPY(DirWatch)
0446 
0447     class Private;
0448     friend class Private;
0449     Private *d;
0450 };
0451 
0452 /**
0453    \class FileWatch qca_support.h QtCrypto
0454 
0455    Support class to monitor a file for activity
0456 
0457    %FileWatch monitors a specified file for any changes. When
0458    the file changes, the changed() signal is emitted.
0459 
0460    \note QFileSystemWatcher has very similar functionality
0461    to this class. You should evaluate this class and
0462    QFileSystemWatcher to determine which better suits your
0463    application needs.
0464 
0465    \ingroup UserAPI
0466 */
0467 class QCA_EXPORT FileWatch : public QObject
0468 {
0469     Q_OBJECT
0470 public:
0471     /**
0472        Standard constructor
0473 
0474        \param file the name of the file to watch. If not
0475        in this object, you can set it using setFileName()
0476        \param parent the parent object for this object
0477     */
0478     explicit FileWatch(const QString &file = QString(), QObject *parent = nullptr);
0479     ~FileWatch() override;
0480 
0481     /**
0482        The name of the file that is being monitored
0483     */
0484     QString fileName() const;
0485 
0486     /**
0487        Change the file being monitored
0488 
0489        \param file the name of the file to monitor
0490     */
0491     void setFileName(const QString &file);
0492 
0493 Q_SIGNALS:
0494     /**
0495        The changed signal is emitted when the file is
0496        changed (e.g. modified, deleted)
0497     */
0498     void changed();
0499 
0500 private:
0501     Q_DISABLE_COPY(FileWatch)
0502 
0503     class Private;
0504     friend class Private;
0505     Private *d;
0506 };
0507 
0508 class ConsolePrivate;
0509 class ConsoleReferencePrivate;
0510 class ConsoleReference;
0511 
0512 /**
0513    \class Console qca_support.h QtCrypto
0514 
0515    %QCA %Console system
0516 
0517    %QCA provides an API for asynchronous, event-based access to
0518    the console and stdin/stdout, as these facilities are
0519    otherwise not portable.  The primary use of this system within
0520    %QCA is for passphrase prompting in command-line applications,
0521    using the tty console type.
0522 
0523    How it works: Create a %Console object for the type of console
0524    desired, and then use ConsoleReference to act on the console.
0525    Only one ConsoleReference may operate on a %Console at a time.
0526 
0527    A %Console object takes over either the physical console (Console::Tty
0528    type) or stdin/stdout (Console::Stdio type).  Only one of each type
0529    may be created at a time.
0530 
0531    Whenever code is written that needs a tty or stdio object, the
0532    code should first call one of the static methods (ttyInstance()
0533    or stdioInstance()) to see if a console object for the desired
0534    type exists already.  If the object exists, use it.  If it does
0535    not exist, the rule is that the relevant code should create the
0536    object, use the object, and then destroy the object when the
0537    operation is completed.
0538 
0539    By following the above rule, you can write code that utilizes
0540    a console without the application having to create some master
0541    console object for you.  Of course, if the application has
0542    created a console then it will be used.
0543 
0544    The reason why there is a master console object is that it
0545    is not guaranteed that all I/O will survive creation and
0546    destruction of a console object.  If you are using the Stdio
0547    Type, then you probably want a long-lived console object.  It
0548    is possible to capture unprocessed I/O by calling
0549    bytesLeftToRead or bytesLeftToWrite.  However, it is not
0550    expected that general console-needing code will call these
0551    functions when utilizing a temporary console.  Thus, an
0552    application developer would need to create his own console
0553    object, invoke the console-needing code, and then do his own
0554    extraction of the unprocessed I/O if necessary.  Another reason
0555    to extract unprocessed I/O is if you need to switch from
0556    %Console back to standard functions (e.g. fgets() ).
0557 
0558    \ingroup UserAPI
0559 */
0560 class QCA_EXPORT Console : public QObject
0561 {
0562     Q_OBJECT
0563 public:
0564     /**
0565        The type of console object
0566     */
0567     enum Type
0568     {
0569         Tty,  ///< physical console
0570         Stdio ///< stdin/stdout
0571     };
0572     /**
0573        The type of I/O to use with the console object.
0574     */
0575     enum ChannelMode
0576     {
0577         Read,     ///< Read only (equivalent to stdin)
0578         ReadWrite ///< Read/write (equivalent to stdin and stdout)
0579     };
0580 
0581     /**
0582        The nature of the console operation
0583     */
0584     enum TerminalMode
0585     {
0586         Default,    ///< use default terminal settings
0587         Interactive ///< char-by-char input, no echo
0588     };
0589 
0590     /**
0591        Standard constructor
0592 
0593        Note that library code should not create a new Console object
0594        without checking whether there is already a Console object of
0595        the required Type. See the main documentation for Console for the
0596        rationale for this.
0597 
0598        \param type the Type of Console object to create
0599        \param cmode the ChannelMode (I/O type) to use
0600        \param tmode the TerminalMode to use
0601        \param parent the parent object for this object
0602 
0603        \sa ttyInstance() and stdioInstance for static methods that allow
0604        you to test whether there is already a Console object of the
0605        required Type, and if there is, obtain a reference to that object.
0606     */
0607     Console(Type type, ChannelMode cmode, TerminalMode tmode, QObject *parent = nullptr);
0608     ~Console() override;
0609 
0610     /**
0611        The Type of this Console object
0612     */
0613     Type type() const;
0614 
0615     /**
0616        The ChannelMode of this Console object
0617     */
0618     ChannelMode channelMode() const;
0619 
0620     /**
0621        The TerminalMode of this Console object
0622     */
0623     TerminalMode terminalMode() const;
0624 
0625     /**
0626        Test whether standard input is redirected.
0627 
0628        \sa type() and channelMode()
0629     */
0630     static bool isStdinRedirected();
0631 
0632     /**
0633        Test whether standard output is redirected.
0634 
0635        \sa type() and channelMode()
0636     */
0637     static bool isStdoutRedirected();
0638 
0639     /**
0640        The current terminal-type console object
0641 
0642        \return null if there is no current Console
0643        of this type, otherwise the Console to use
0644     */
0645     static Console *ttyInstance();
0646 
0647     /**
0648        The current stdio-type console object
0649 
0650        \return null if there is no current Console
0651        of this type, otherwise the Console to use
0652     */
0653     static Console *stdioInstance();
0654 
0655     /**
0656       Release the Console
0657 
0658       This allows access to buffers containing any remaining data
0659     */
0660     void release();
0661 
0662     /**
0663        Obtain remaining data from the Console, awaiting
0664        a read operation
0665     */
0666     QByteArray bytesLeftToRead();
0667 
0668     /**
0669        Obtain remaining data from the Console, awaiting
0670        a write operation
0671     */
0672     QByteArray bytesLeftToWrite();
0673 
0674 private:
0675     Q_DISABLE_COPY(Console)
0676 
0677     friend class ConsolePrivate;
0678     ConsolePrivate *d;
0679 
0680     friend class ConsoleReference;
0681 };
0682 
0683 /**
0684    \class ConsoleReference qca_support.h QtCrypto
0685 
0686    Manager for a Console
0687 
0688    \note Only one %ConsoleReference object can be active at a time
0689 
0690    \ingroup UserAPI
0691 */
0692 class QCA_EXPORT ConsoleReference : public QObject
0693 {
0694     Q_OBJECT
0695 public:
0696     /**
0697        The security setting to use for the Console being managed.
0698     */
0699     enum SecurityMode
0700     {
0701         SecurityDisabled,
0702         SecurityEnabled
0703     };
0704 
0705     /**
0706        Standard constructor
0707 
0708        \param parent the parent object for this object
0709     */
0710     ConsoleReference(QObject *parent = nullptr);
0711     ~ConsoleReference() override;
0712 
0713     /**
0714        Set the Console object to be managed, and start processing.
0715 
0716        You typically want to use Console::ttyInstance() or
0717        Console::stdioInstance() to obtain the required Console
0718        reference.
0719 
0720        \param console reference to the Console to be managed
0721        \param mode the SecurityMode to use for this Console.
0722 
0723        \sa QCA::Console for more information on how to handle the
0724        console aspects of your application or library code.
0725     */
0726     bool start(Console *console, SecurityMode mode = SecurityDisabled);
0727 
0728     /**
0729        Stop processing, and release the Console
0730     */
0731     void stop();
0732 
0733     /**
0734        The Console object managed by this object
0735 
0736        \sa start() to set the Console to be managed
0737     */
0738     Console *console() const;
0739 
0740     /**
0741        The security mode setting for the Console object
0742        managed by this object.
0743 
0744        \sa start() to set the SecurityMode
0745     */
0746     SecurityMode securityMode() const;
0747 
0748     /**
0749        Read data from the Console.
0750 
0751        \param bytes the number of bytes to read. The default
0752        is to read all available bytes
0753 
0754        \sa readSecure() for a method suitable for reading
0755        sensitive data.
0756     */
0757     QByteArray read(int bytes = -1);
0758 
0759     /**
0760        Write data to the Console.
0761 
0762        \param a the array of data to write to the Console
0763 
0764        \sa writeSecure() for a method suitable for writing
0765        sensitive data.
0766     */
0767     void write(const QByteArray &a);
0768 
0769     /**
0770        Read secure data from the Console
0771 
0772        \param bytes the number of bytes to read. The default
0773        is to read all available bytes
0774 
0775        \sa read() which is suitable for non-sensitive data
0776     */
0777     SecureArray readSecure(int bytes = -1);
0778 
0779     /**
0780        Write secure data to the Console
0781 
0782        \param a the array of data to write to the Console
0783 
0784        \sa write() which is suitable for non-sensitive data
0785     */
0786     void writeSecure(const SecureArray &a);
0787 
0788     /**
0789        Close the write channel
0790 
0791        You only need to call this if writing is enabled
0792        on the Console being managed.
0793     */
0794     void closeOutput();
0795 
0796     /**
0797        The number of bytes available to read from the
0798        Console being managed.
0799     */
0800     int bytesAvailable() const;
0801 
0802     /**
0803        The number of bytes remaining to be written
0804        to the Console being managed
0805     */
0806     int bytesToWrite() const;
0807 
0808 Q_SIGNALS:
0809     /**
0810        Emitted when there are bytes available to read from
0811        the Console being managed
0812     */
0813     void readyRead();
0814 
0815     /**
0816        Emitted when bytes are written to the Console
0817 
0818        \param bytes the number of bytes that were written
0819 
0820        \sa bytesAvailable()
0821     */
0822     void bytesWritten(int bytes);
0823 
0824     /**
0825        Emitted when the console input is closed
0826     */
0827     void inputClosed();
0828 
0829     /**
0830        Emitted when the console output is closed
0831     */
0832     void outputClosed();
0833 
0834 private:
0835     Q_DISABLE_COPY(ConsoleReference)
0836 
0837     friend class ConsoleReferencePrivate;
0838     ConsoleReferencePrivate *d;
0839 
0840     friend class Console;
0841 };
0842 
0843 /**
0844    \class ConsolePrompt qca_support.h QtCrypto
0845 
0846    Console prompt handler.
0847 
0848    This class provides a convenient way to get user input in a secure way,
0849 as shown below:
0850 \code
0851 QCA::ConsolePrompt prompt;
0852 prompt.getHidden("Passphrase");
0853 prompt.waitForFinished();
0854 QCA:SecureArray pass = prompt.result();
0855 \endcode
0856 
0857    \note It is not necessary to use waitForFinished(), because you can
0858    just connect the finished() signal to a suitable method, however
0859    command line (console) applications often require waitForFinished().
0860 
0861    \ingroup UserAPI
0862 */
0863 class QCA_EXPORT ConsolePrompt : public QObject
0864 {
0865     Q_OBJECT
0866 public:
0867     /**
0868        Standard constructor
0869 
0870        \param parent the parent object for this object
0871     */
0872     ConsolePrompt(QObject *parent = nullptr);
0873     ~ConsolePrompt() override;
0874 
0875     /**
0876        Allow the user to enter data without it being echo'd to
0877        the terminal. This is particularly useful for entry
0878        of passwords, passphrases and PINs.
0879 
0880        \param promptStr the prompt to display to the user
0881 
0882        \sa result() for how to get the input back.
0883     */
0884     void getHidden(const QString &promptStr);
0885 
0886     /**
0887        Obtain one character from the user
0888 
0889        \sa resultChar() for how to get the input back.
0890     */
0891     void getChar();
0892 
0893     /**
0894        Block waiting for user input.
0895 
0896        You may wish to use the finished() signal to
0897        avoid blocking.
0898     */
0899     void waitForFinished();
0900 
0901     /**
0902        Obtain the result of the user input.
0903 
0904        This method is usually called to obtain data
0905        from the user that was requested by the getHidden()
0906        call.
0907     */
0908     SecureArray result() const;
0909 
0910     /**
0911        Obtain the result of the user input.
0912 
0913        This method is usually called to obtain data
0914        from the user that was requested by the getChar()
0915        call.
0916     */
0917     QChar resultChar() const;
0918 
0919 Q_SIGNALS:
0920     /**
0921        Emitted when the user input activity has been
0922        completed.
0923 
0924        This corresponds to the provision of a string
0925        for getHidden() or a single character for getChar().
0926 
0927        \sa waitForFinished
0928     */
0929     void finished();
0930 
0931 private:
0932     Q_DISABLE_COPY(ConsolePrompt)
0933 
0934     class Private;
0935     friend class Private;
0936     Private *d;
0937 };
0938 
0939 class AbstractLogDevice;
0940 
0941 /**
0942    \class Logger qca_support.h QtCrypto
0943 
0944    A simple logging system
0945 
0946    This class provides a simple but flexible approach to logging information
0947    that may be used for debugging or system operation diagnostics.
0948 
0949    There is a single %Logger for each application that uses %QCA. You do not
0950    need to create this %Logger yourself - %QCA automatically creates it on
0951    startup. You can get access to the %Logger using the global QCA::logger()
0952    method.
0953 
0954    By default the Logger just accepts all messages (binary and text). If you
0955    want to get access to those messages, you need to subclass
0956    AbstractLogDevice, and register your subclass (using registerLogDevice()).
0957    You can then take whatever action is appropriate (e.g. show to the user
0958    using the GUI, log to a file or send to standard error).
0959 
0960    \ingroup UserAPI
0961 */
0962 class QCA_EXPORT Logger : public QObject
0963 {
0964     Q_OBJECT
0965 public:
0966     /**
0967        The severity of the message
0968 
0969        This information may be used by the log device to determine
0970        what the appropriate action is.
0971     */
0972     enum Severity
0973     {
0974         Quiet       = 0, ///< Quiet: turn of logging
0975         Emergency   = 1, ///< Emergency: system is unusable
0976         Alert       = 2, ///< Alert: action must be taken immediately
0977         Critical    = 3, ///< Critical: critical conditions
0978         Error       = 4, ///< Error: error conditions
0979         Warning     = 5, ///< Warning: warning conditions
0980         Notice      = 6, ///< Notice: normal but significant condition
0981         Information = 7, ///< Informational: informational messages
0982         Debug       = 8  ///< Debug: debug-level messages
0983     };
0984 
0985     /**
0986        Get the current logging level
0987 
0988        \return Current level
0989     */
0990     inline Severity level() const
0991     {
0992         return m_logLevel;
0993     }
0994 
0995     /**
0996        Set the current logging level
0997 
0998        \param level new logging level
0999 
1000        Only severities less or equal than the log level one will be logged
1001     */
1002     void setLevel(Severity level);
1003 
1004     /**
1005        Log a message to all available log devices
1006 
1007        \param message the text to log
1008     */
1009     void logTextMessage(const QString &message, Severity = Information);
1010 
1011     /**
1012        Log a binary blob to all available log devices
1013 
1014        \param blob the information to log
1015 
1016        \note how this is handled is quite logger specific. For
1017        example, it might be logged as a binary, or it might be
1018        encoded in some way
1019     */
1020     void logBinaryMessage(const QByteArray &blob, Severity = Information);
1021 
1022     /**
1023        Add an AbstractLogDevice subclass to the existing list of loggers
1024 
1025        \param logger the LogDevice to add
1026     */
1027     void registerLogDevice(AbstractLogDevice *logger);
1028 
1029     /**
1030        Remove an AbstractLogDevice subclass from the existing list of loggers
1031 
1032        \param loggerName the name of the LogDevice to remove
1033 
1034        \note If there are several log devices with the same name, all will be removed.
1035     */
1036     void unregisterLogDevice(const QString &loggerName);
1037 
1038     /**
1039        Get a list of the names of all registered log devices
1040     */
1041     QStringList currentLogDevices() const;
1042 
1043 private:
1044     Q_DISABLE_COPY(Logger)
1045 
1046     friend class Global;
1047 
1048     /**
1049        Create a new message logger
1050     */
1051     Logger();
1052 
1053     ~Logger() override;
1054 
1055     QStringList                m_loggerNames;
1056     QList<AbstractLogDevice *> m_loggers;
1057     Severity                   m_logLevel;
1058 };
1059 
1060 /**
1061    \class AbstractLogDevice qca_support.h QtCrypto
1062 
1063    An abstract log device
1064 
1065    \ingroup UserAPI
1066 */
1067 class QCA_EXPORT AbstractLogDevice : public QObject
1068 {
1069     Q_OBJECT
1070 public:
1071     /**
1072        The name of this log device
1073     */
1074     QString name() const;
1075 
1076     /**
1077        Log a message
1078 
1079        The default implementation does nothing - you should
1080        override this method in your subclass to do whatever
1081        logging is required
1082 
1083        \param message the message to log
1084        \param severity the severity level of the message
1085     */
1086     virtual void logTextMessage(const QString &message, Logger::Severity severity);
1087 
1088     /**
1089        Log a binary blob
1090 
1091        The default implementation does nothing - you should
1092        override this method in your subclass to do whatever
1093        logging is required
1094 
1095        \param blob the message (as a byte array) to log
1096        \param severity the severity level of the message
1097     */
1098     virtual void logBinaryMessage(const QByteArray &blob, Logger::Severity severity);
1099 
1100 protected:
1101     /**
1102        Create a new message logger
1103 
1104        \param name the name of this log device
1105        \param parent the parent for this logger
1106     */
1107     explicit AbstractLogDevice(const QString &name, QObject *parent = nullptr);
1108 
1109     ~AbstractLogDevice() override = 0;
1110 
1111 private:
1112     Q_DISABLE_COPY(AbstractLogDevice)
1113 
1114     class Private;
1115     Private *d;
1116 
1117     QString m_name;
1118 };
1119 
1120 }
1121 
1122 #endif