~ubuntu-branches/debian/squeeze/pycryptopp/squeeze

« back to all changes in this revision

Viewing changes to cryptopp/cryptlib.h

  • Committer: Bazaar Package Importer
  • Author(s): Zooko O'Whielacronx
  • Date: 2009-06-22 22:20:50 UTC
  • Revision ID: james.westby@ubuntu.com-20090622222050-hbqmn50dt2kvoz5o
Tags: upstream-0.5.14
ImportĀ upstreamĀ versionĀ 0.5.14

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
// cryptlib.h - written and placed in the public domain by Wei Dai
 
2
/*! \file
 
3
        This file contains the declarations for the abstract base
 
4
        classes that provide a uniform interface to this library.
 
5
*/
 
6
 
 
7
/*!     \mainpage Crypto++ Library 5.6.0 API Reference
 
8
<dl>
 
9
<dt>Abstract Base Classes<dd>
 
10
        cryptlib.h
 
11
<dt>Authenticated Encryption<dd>
 
12
        AuthenticatedSymmetricCipherDocumentation
 
13
<dt>Symmetric Ciphers<dd>
 
14
        SymmetricCipherDocumentation
 
15
<dt>Hash Functions<dd>
 
16
        SHA1, SHA224, SHA256, SHA384, SHA512, Tiger, Whirlpool, RIPEMD160, RIPEMD320, RIPEMD128, RIPEMD256, Weak1::MD2, Weak1::MD4, Weak1::MD5
 
17
<dt>Non-Cryptographic Checksums<dd>
 
18
        CRC32, Adler32
 
19
<dt>Message Authentication Codes<dd>
 
20
        VMAC, HMAC, CBC_MAC, CMAC, DMAC, TTMAC, GCM (GMAC)
 
21
<dt>Random Number Generators<dd>
 
22
        NullRNG(), LC_RNG, RandomPool, BlockingRng, NonblockingRng, AutoSeededRandomPool, AutoSeededX917RNG, DefaultAutoSeededRNG
 
23
<dt>Password-based Cryptography<dd>
 
24
        PasswordBasedKeyDerivationFunction
 
25
<dt>Public Key Cryptosystems<dd>
 
26
        DLIES, ECIES, LUCES, RSAES, RabinES, LUC_IES
 
27
<dt>Public Key Signature Schemes<dd>
 
28
        DSA, GDSA, ECDSA, NR, ECNR, LUCSS, RSASS, RSASS_ISO, RabinSS, RWSS, ESIGN
 
29
<dt>Key Agreement<dd>
 
30
        #DH, DH2, #MQV, ECDH, ECMQV, XTR_DH
 
31
<dt>Algebraic Structures<dd>
 
32
        Integer, PolynomialMod2, PolynomialOver, RingOfPolynomialsOver,
 
33
        ModularArithmetic, MontgomeryRepresentation, GFP2_ONB,
 
34
        GF2NP, GF256, GF2_32, EC2N, ECP
 
35
<dt>Secret Sharing and Information Dispersal<dd>
 
36
        SecretSharing, SecretRecovery, InformationDispersal, InformationRecovery
 
37
<dt>Compression<dd>
 
38
        Deflator, Inflator, Gzip, Gunzip, ZlibCompressor, ZlibDecompressor
 
39
<dt>Input Source Classes<dd>
 
40
        StringSource, ArraySource, FileSource, SocketSource, WindowsPipeSource, RandomNumberSource
 
41
<dt>Output Sink Classes<dd>
 
42
        StringSinkTemplate, ArraySink, FileSink, SocketSink, WindowsPipeSink, RandomNumberSink
 
43
<dt>Filter Wrappers<dd>
 
44
        StreamTransformationFilter, HashFilter, HashVerificationFilter, SignerFilter, SignatureVerificationFilter
 
45
<dt>Binary to Text Encoders and Decoders<dd>
 
46
        HexEncoder, HexDecoder, Base64Encoder, Base64Decoder, Base32Encoder, Base32Decoder
 
47
<dt>Wrappers for OS features<dd>
 
48
        Timer, Socket, WindowsHandle, ThreadLocalStorage, ThreadUserTimer
 
49
<dt>FIPS 140 related<dd>
 
50
        fips140.h
 
51
</dl>
 
52
 
 
53
In the FIPS 140-2 validated DLL version of Crypto++, only the following implementation class are available.
 
54
<dl>
 
55
<dt>Block Ciphers<dd>
 
56
        AES, DES_EDE2, DES_EDE3, SKIPJACK
 
57
<dt>Cipher Modes (replace template parameter BC with one of the block ciphers above)<dd>
 
58
        ECB_Mode\<BC\>, CTR_Mode\<BC\>, CBC_Mode\<BC\>, CFB_FIPS_Mode\<BC\>, OFB_Mode\<BC\>
 
59
<dt>Hash Functions<dd>
 
60
        SHA1, SHA224, SHA256, SHA384, SHA512
 
61
<dt>Public Key Signature Schemes (replace template parameter H with one of the hash functions above)<dd>
 
62
        RSASS\<PKCS1v15, H\>, RSASS\<PSS, H\>, RSASS_ISO\<H\>, RWSS\<P1363_EMSA2, H\>, DSA, ECDSA\<ECP, H\>, ECDSA\<EC2N, H\>
 
63
<dt>Message Authentication Codes (replace template parameter H with one of the hash functions above)<dd>
 
64
        HMAC\<H\>, CBC_MAC\<DES_EDE2\>, CBC_MAC\<DES_EDE3\>
 
65
<dt>Random Number Generators<dd>
 
66
        DefaultAutoSeededRNG (AutoSeededX917RNG\<AES\>)
 
67
<dt>Key Agreement<dd>
 
68
        #DH
 
69
<dt>Public Key Cryptosystems<dd>
 
70
        RSAES\<OAEP\<SHA1\> \>
 
71
</dl>
 
72
 
 
73
<p>This reference manual is a work in progress. Some classes are still lacking detailed descriptions.
 
74
<p>Click <a href="CryptoPPRef.zip">here</a> to download a zip archive containing this manual.
 
75
<p>Thanks to Ryan Phillips for providing the Doxygen configuration file
 
76
and getting me started with this manual.
 
77
*/
 
78
 
 
79
#ifndef CRYPTOPP_CRYPTLIB_H
 
80
#define CRYPTOPP_CRYPTLIB_H
 
81
 
 
82
#include "config.h"
 
83
#include "stdcpp.h"
 
84
 
 
85
NAMESPACE_BEGIN(CryptoPP)
 
86
 
 
87
// forward declarations
 
88
class Integer;
 
89
class RandomNumberGenerator;
 
90
class BufferedTransformation;
 
91
 
 
92
//! used to specify a direction for a cipher to operate in (encrypt or decrypt)
 
93
enum CipherDir {ENCRYPTION, DECRYPTION};
 
94
 
 
95
//! used to represent infinite time
 
96
const unsigned long INFINITE_TIME = ULONG_MAX;
 
97
 
 
98
// VC60 workaround: using enums as template parameters causes problems
 
99
template <typename ENUM_TYPE, int VALUE>
 
100
struct EnumToType
 
101
{
 
102
        static ENUM_TYPE ToEnum() {return (ENUM_TYPE)VALUE;}
 
103
};
 
104
 
 
105
enum ByteOrder {LITTLE_ENDIAN_ORDER = 0, BIG_ENDIAN_ORDER = 1};
 
106
typedef EnumToType<ByteOrder, LITTLE_ENDIAN_ORDER> LittleEndian;
 
107
typedef EnumToType<ByteOrder, BIG_ENDIAN_ORDER> BigEndian;
 
108
 
 
109
//! base class for all exceptions thrown by Crypto++
 
110
class CRYPTOPP_DLL Exception : public std::exception
 
111
{
 
112
public:
 
113
        //! error types
 
114
        enum ErrorType {
 
115
                //! a method is not implemented
 
116
                NOT_IMPLEMENTED,
 
117
                //! invalid function argument
 
118
                INVALID_ARGUMENT,
 
119
                //! BufferedTransformation received a Flush(true) signal but can't flush buffers
 
120
                CANNOT_FLUSH,
 
121
                //! data integerity check (such as CRC or MAC) failed
 
122
                DATA_INTEGRITY_CHECK_FAILED,
 
123
                //! received input data that doesn't conform to expected format
 
124
                INVALID_DATA_FORMAT,
 
125
                //! error reading from input device or writing to output device
 
126
                IO_ERROR,
 
127
                //! some error not belong to any of the above categories
 
128
                OTHER_ERROR
 
129
        };
 
130
 
 
131
        explicit Exception(ErrorType errorType, const std::string &s) : m_errorType(errorType), m_what(s) {}
 
132
        virtual ~Exception() throw() {}
 
133
        const char *what() const throw() {return (m_what.c_str());}
 
134
        const std::string &GetWhat() const {return m_what;}
 
135
        void SetWhat(const std::string &s) {m_what = s;}
 
136
        ErrorType GetErrorType() const {return m_errorType;}
 
137
        void SetErrorType(ErrorType errorType) {m_errorType = errorType;}
 
138
 
 
139
private:
 
140
        ErrorType m_errorType;
 
141
        std::string m_what;
 
142
};
 
143
 
 
144
//! exception thrown when an invalid argument is detected
 
145
class CRYPTOPP_DLL InvalidArgument : public Exception
 
146
{
 
147
public:
 
148
        explicit InvalidArgument(const std::string &s) : Exception(INVALID_ARGUMENT, s) {}
 
149
};
 
150
 
 
151
//! exception thrown when input data is received that doesn't conform to expected format
 
152
class CRYPTOPP_DLL InvalidDataFormat : public Exception
 
153
{
 
154
public:
 
155
        explicit InvalidDataFormat(const std::string &s) : Exception(INVALID_DATA_FORMAT, s) {}
 
156
};
 
157
 
 
158
//! exception thrown by decryption filters when trying to decrypt an invalid ciphertext
 
159
class CRYPTOPP_DLL InvalidCiphertext : public InvalidDataFormat
 
160
{
 
161
public:
 
162
        explicit InvalidCiphertext(const std::string &s) : InvalidDataFormat(s) {}
 
163
};
 
164
 
 
165
//! exception thrown by a class if a non-implemented method is called
 
166
class CRYPTOPP_DLL NotImplemented : public Exception
 
167
{
 
168
public:
 
169
        explicit NotImplemented(const std::string &s) : Exception(NOT_IMPLEMENTED, s) {}
 
170
};
 
171
 
 
172
//! exception thrown by a class when Flush(true) is called but it can't completely flush its buffers
 
173
class CRYPTOPP_DLL CannotFlush : public Exception
 
174
{
 
175
public:
 
176
        explicit CannotFlush(const std::string &s) : Exception(CANNOT_FLUSH, s) {}
 
177
};
 
178
 
 
179
//! error reported by the operating system
 
180
class CRYPTOPP_DLL OS_Error : public Exception
 
181
{
 
182
public:
 
183
        OS_Error(ErrorType errorType, const std::string &s, const std::string& operation, int errorCode)
 
184
                : Exception(errorType, s), m_operation(operation), m_errorCode(errorCode) {}
 
185
        ~OS_Error() throw() {}
 
186
 
 
187
        // the operating system API that reported the error
 
188
        const std::string & GetOperation() const {return m_operation;}
 
189
        // the error code return by the operating system
 
190
        int GetErrorCode() const {return m_errorCode;}
 
191
 
 
192
protected:
 
193
        std::string m_operation;
 
194
        int m_errorCode;
 
195
};
 
196
 
 
197
//! used to return decoding results
 
198
struct CRYPTOPP_DLL DecodingResult
 
199
{
 
200
        explicit DecodingResult() : isValidCoding(false), messageLength(0) {}
 
201
        explicit DecodingResult(size_t len) : isValidCoding(true), messageLength(len) {}
 
202
 
 
203
        bool operator==(const DecodingResult &rhs) const {return isValidCoding == rhs.isValidCoding && messageLength == rhs.messageLength;}
 
204
        bool operator!=(const DecodingResult &rhs) const {return !operator==(rhs);}
 
205
 
 
206
        bool isValidCoding;
 
207
        size_t messageLength;
 
208
 
 
209
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
210
        operator size_t() const {return isValidCoding ? messageLength : 0;}
 
211
#endif
 
212
};
 
213
 
 
214
//! interface for retrieving values given their names
 
215
/*! \note This class is used to safely pass a variable number of arbitrarily typed arguments to functions
 
216
        and to read values from keys and crypto parameters.
 
217
        \note To obtain an object that implements NameValuePairs for the purpose of parameter
 
218
        passing, use the MakeParameters() function.
 
219
        \note To get a value from NameValuePairs, you need to know the name and the type of the value. 
 
220
        Call GetValueNames() on a NameValuePairs object to obtain a list of value names that it supports.
 
221
        Then look at the Name namespace documentation to see what the type of each value is, or
 
222
        alternatively, call GetIntValue() with the value name, and if the type is not int, a
 
223
        ValueTypeMismatch exception will be thrown and you can get the actual type from the exception object.
 
224
*/
 
225
class CRYPTOPP_NO_VTABLE NameValuePairs
 
226
{
 
227
public:
 
228
        virtual ~NameValuePairs() {}
 
229
 
 
230
        //! exception thrown when trying to retrieve a value using a different type than expected
 
231
        class CRYPTOPP_DLL ValueTypeMismatch : public InvalidArgument
 
232
        {
 
233
        public:
 
234
                ValueTypeMismatch(const std::string &name, const std::type_info &stored, const std::type_info &retrieving)
 
235
                        : InvalidArgument("NameValuePairs: type mismatch for '" + name + "', stored '" + stored.name() + "', trying to retrieve '" + retrieving.name() + "'")
 
236
                        , m_stored(stored), m_retrieving(retrieving) {}
 
237
 
 
238
                const std::type_info & GetStoredTypeInfo() const {return m_stored;}
 
239
                const std::type_info & GetRetrievingTypeInfo() const {return m_retrieving;}
 
240
 
 
241
        private:
 
242
                const std::type_info &m_stored;
 
243
                const std::type_info &m_retrieving;
 
244
        };
 
245
 
 
246
        //! get a copy of this object or a subobject of it
 
247
        template <class T>
 
248
        bool GetThisObject(T &object) const
 
249
        {
 
250
                return GetValue((std::string("ThisObject:")+typeid(T).name()).c_str(), object);
 
251
        }
 
252
 
 
253
        //! get a pointer to this object, as a pointer to T
 
254
        template <class T>
 
255
        bool GetThisPointer(T *&p) const
 
256
        {
 
257
                return GetValue((std::string("ThisPointer:")+typeid(T).name()).c_str(), p);
 
258
        }
 
259
 
 
260
        //! get a named value, returns true if the name exists
 
261
        template <class T>
 
262
        bool GetValue(const char *name, T &value) const
 
263
        {
 
264
                return GetVoidValue(name, typeid(T), &value);
 
265
        }
 
266
 
 
267
        //! get a named value, returns the default if the name doesn't exist
 
268
        template <class T>
 
269
        T GetValueWithDefault(const char *name, T defaultValue) const
 
270
        {
 
271
                GetValue(name, defaultValue);
 
272
                return defaultValue;
 
273
        }
 
274
 
 
275
        //! get a list of value names that can be retrieved
 
276
        CRYPTOPP_DLL std::string GetValueNames() const
 
277
                {std::string result; GetValue("ValueNames", result); return result;}
 
278
 
 
279
        //! get a named value with type int
 
280
        /*! used to ensure we don't accidentally try to get an unsigned int
 
281
                or some other type when we mean int (which is the most common case) */
 
282
        CRYPTOPP_DLL bool GetIntValue(const char *name, int &value) const
 
283
                {return GetValue(name, value);}
 
284
 
 
285
        //! get a named value with type int, with default
 
286
        CRYPTOPP_DLL int GetIntValueWithDefault(const char *name, int defaultValue) const
 
287
                {return GetValueWithDefault(name, defaultValue);}
 
288
 
 
289
        //! used by derived classes to check for type mismatch
 
290
        CRYPTOPP_DLL static void CRYPTOPP_API ThrowIfTypeMismatch(const char *name, const std::type_info &stored, const std::type_info &retrieving)
 
291
                {if (stored != retrieving) throw ValueTypeMismatch(name, stored, retrieving);}
 
292
 
 
293
        template <class T>
 
294
        void GetRequiredParameter(const char *className, const char *name, T &value) const
 
295
        {
 
296
                if (!GetValue(name, value))
 
297
                        throw InvalidArgument(std::string(className) + ": missing required parameter '" + name + "'");
 
298
        }
 
299
 
 
300
        CRYPTOPP_DLL void GetRequiredIntParameter(const char *className, const char *name, int &value) const
 
301
        {
 
302
                if (!GetIntValue(name, value))
 
303
                        throw InvalidArgument(std::string(className) + ": missing required parameter '" + name + "'");
 
304
        }
 
305
 
 
306
        //! to be implemented by derived classes, users should use one of the above functions instead
 
307
        CRYPTOPP_DLL virtual bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const =0;
 
308
};
 
309
 
 
310
//! namespace containing value name definitions
 
311
/*!     value names, types and semantics:
 
312
 
 
313
        ThisObject:ClassName (ClassName, copy of this object or a subobject)
 
314
        ThisPointer:ClassName (const ClassName *, pointer to this object or a subobject)
 
315
*/
 
316
DOCUMENTED_NAMESPACE_BEGIN(Name)
 
317
// more names defined in argnames.h
 
318
DOCUMENTED_NAMESPACE_END
 
319
 
 
320
//! empty set of name-value pairs
 
321
class CRYPTOPP_DLL NullNameValuePairs : public NameValuePairs
 
322
{
 
323
public:
 
324
        bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const {return false;}
 
325
};
 
326
 
 
327
//! _
 
328
extern CRYPTOPP_DLL const NullNameValuePairs g_nullNameValuePairs;
 
329
 
 
330
// ********************************************************
 
331
 
 
332
//! interface for cloning objects, this is not implemented by most classes yet
 
333
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Clonable
 
334
{
 
335
public:
 
336
        virtual ~Clonable() {}
 
337
        //! this is not implemented by most classes yet
 
338
        virtual Clonable* Clone() const {throw NotImplemented("Clone() is not implemented yet.");}      // TODO: make this =0
 
339
};
 
340
 
 
341
//! interface for all crypto algorithms
 
342
 
 
343
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Algorithm : public Clonable
 
344
{
 
345
public:
 
346
        /*! When FIPS 140-2 compliance is enabled and checkSelfTestStatus == true,
 
347
                this constructor throws SelfTestFailure if the self test hasn't been run or fails. */
 
348
        Algorithm(bool checkSelfTestStatus = true);
 
349
        //! returns name of this algorithm, not universally implemented yet
 
350
        virtual std::string AlgorithmName() const {return "unknown";}
 
351
};
 
352
 
 
353
//! keying interface for crypto algorithms that take byte strings as keys
 
354
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE SimpleKeyingInterface
 
355
{
 
356
public:
 
357
        virtual ~SimpleKeyingInterface() {}
 
358
 
 
359
        //! returns smallest valid key length in bytes */
 
360
        virtual size_t MinKeyLength() const =0;
 
361
        //! returns largest valid key length in bytes */
 
362
        virtual size_t MaxKeyLength() const =0;
 
363
        //! returns default (recommended) key length in bytes */
 
364
        virtual size_t DefaultKeyLength() const =0;
 
365
 
 
366
        //! returns the smallest valid key length in bytes that is >= min(n, GetMaxKeyLength())
 
367
        virtual size_t GetValidKeyLength(size_t n) const =0;
 
368
 
 
369
        //! returns whether n is a valid key length
 
370
        virtual bool IsValidKeyLength(size_t n) const
 
371
                {return n == GetValidKeyLength(n);}
 
372
 
 
373
        //! set or reset the key of this object
 
374
        /*! \param params is used to specify Rounds, BlockSize, etc. */
 
375
        virtual void SetKey(const byte *key, size_t length, const NameValuePairs &params = g_nullNameValuePairs);
 
376
 
 
377
        //! calls SetKey() with an NameValuePairs object that just specifies "Rounds"
 
378
        void SetKeyWithRounds(const byte *key, size_t length, int rounds);
 
379
 
 
380
        //! calls SetKey() with an NameValuePairs object that just specifies "IV"
 
381
        void SetKeyWithIV(const byte *key, size_t length, const byte *iv, size_t ivLength);
 
382
 
 
383
        //! calls SetKey() with an NameValuePairs object that just specifies "IV"
 
384
        void SetKeyWithIV(const byte *key, size_t length, const byte *iv)
 
385
                {SetKeyWithIV(key, length, iv, IVSize());}
 
386
 
 
387
        enum IV_Requirement {UNIQUE_IV = 0, RANDOM_IV, UNPREDICTABLE_RANDOM_IV, INTERNALLY_GENERATED_IV, NOT_RESYNCHRONIZABLE};
 
388
        //! returns the minimal requirement for secure IVs
 
389
        virtual IV_Requirement IVRequirement() const =0;
 
390
 
 
391
        //! returns whether this object can be resynchronized (i.e. supports initialization vectors)
 
392
        /*! If this function returns true, and no IV is passed to SetKey() and CanUseStructuredIVs()==true, an IV of all 0's will be assumed. */
 
393
        bool IsResynchronizable() const {return IVRequirement() < NOT_RESYNCHRONIZABLE;}
 
394
        //! returns whether this object can use random IVs (in addition to ones returned by GetNextIV)
 
395
        bool CanUseRandomIVs() const {return IVRequirement() <= UNPREDICTABLE_RANDOM_IV;}
 
396
        //! returns whether this object can use random but possibly predictable IVs (in addition to ones returned by GetNextIV)
 
397
        bool CanUsePredictableIVs() const {return IVRequirement() <= RANDOM_IV;}
 
398
        //! returns whether this object can use structured IVs, for example a counter (in addition to ones returned by GetNextIV)
 
399
        bool CanUseStructuredIVs() const {return IVRequirement() <= UNIQUE_IV;}
 
400
 
 
401
        virtual unsigned int IVSize() const {throw NotImplemented(GetAlgorithm().AlgorithmName() + ": this object doesn't support resynchronization");}
 
402
        //! returns default length of IVs accepted by this object
 
403
        unsigned int DefaultIVLength() const {return IVSize();}
 
404
        //! returns minimal length of IVs accepted by this object
 
405
        virtual unsigned int MinIVLength() const {return IVSize();}
 
406
        //! returns maximal length of IVs accepted by this object
 
407
        virtual unsigned int MaxIVLength() const {return IVSize();}
 
408
        //! resynchronize with an IV. ivLength=-1 means use IVSize()
 
409
        virtual void Resynchronize(const byte *iv, int ivLength=-1) {throw NotImplemented(GetAlgorithm().AlgorithmName() + ": this object doesn't support resynchronization");}
 
410
        //! get a secure IV for the next message
 
411
        /*! This method should be called after you finish encrypting one message and are ready to start the next one.
 
412
                After calling it, you must call SetKey() or Resynchronize() before using this object again. 
 
413
                This method is not implemented on decryption objects. */
 
414
        virtual void GetNextIV(RandomNumberGenerator &rng, byte *IV);
 
415
 
 
416
protected:
 
417
        virtual const Algorithm & GetAlgorithm() const =0;
 
418
        virtual void UncheckedSetKey(const byte *key, unsigned int length, const NameValuePairs &params) =0;
 
419
 
 
420
        void ThrowIfInvalidKeyLength(size_t length);
 
421
        void ThrowIfResynchronizable();                 // to be called when no IV is passed
 
422
        void ThrowIfInvalidIV(const byte *iv);  // check for NULL IV if it can't be used
 
423
        size_t ThrowIfInvalidIVLength(int size);
 
424
        const byte * GetIVAndThrowIfInvalid(const NameValuePairs &params, size_t &size);
 
425
        inline void AssertValidKeyLength(size_t length) const
 
426
                {assert(IsValidKeyLength(length));}
 
427
};
 
428
 
 
429
//! interface for the data processing part of block ciphers
 
430
 
 
431
/*! Classes derived from BlockTransformation are block ciphers
 
432
        in ECB mode (for example the DES::Encryption class), which are stateless.
 
433
        These classes should not be used directly, but only in combination with
 
434
        a mode class (see CipherModeDocumentation in modes.h).
 
435
*/
 
436
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE BlockTransformation : public Algorithm
 
437
{
 
438
public:
 
439
        //! encrypt or decrypt inBlock, xor with xorBlock, and write to outBlock
 
440
        virtual void ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const =0;
 
441
 
 
442
        //! encrypt or decrypt one block
 
443
        /*! \pre size of inBlock and outBlock == BlockSize() */
 
444
        void ProcessBlock(const byte *inBlock, byte *outBlock) const
 
445
                {ProcessAndXorBlock(inBlock, NULL, outBlock);}
 
446
 
 
447
        //! encrypt or decrypt one block in place
 
448
        void ProcessBlock(byte *inoutBlock) const
 
449
                {ProcessAndXorBlock(inoutBlock, NULL, inoutBlock);}
 
450
 
 
451
        //! block size of the cipher in bytes
 
452
        virtual unsigned int BlockSize() const =0;
 
453
 
 
454
        //! returns how inputs and outputs should be aligned for optimal performance
 
455
        virtual unsigned int OptimalDataAlignment() const;
 
456
 
 
457
        //! returns true if this is a permutation (i.e. there is an inverse transformation)
 
458
        virtual bool IsPermutation() const {return true;}
 
459
 
 
460
        //! returns true if this is an encryption object
 
461
        virtual bool IsForwardTransformation() const =0;
 
462
 
 
463
        //! return number of blocks that can be processed in parallel, for bit-slicing implementations
 
464
        virtual unsigned int OptimalNumberOfParallelBlocks() const {return 1;}
 
465
 
 
466
        enum {BT_InBlockIsCounter=1, BT_DontIncrementInOutPointers=2, BT_XorInput=4, BT_ReverseDirection=8} FlagsForAdvancedProcessBlocks;
 
467
 
 
468
        //! encrypt and xor blocks according to flags (see FlagsForAdvancedProcessBlocks)
 
469
        /*! /note If BT_InBlockIsCounter is set, last byte of inBlocks may be modified. */
 
470
        virtual size_t AdvancedProcessBlocks(const byte *inBlocks, const byte *xorBlocks, byte *outBlocks, size_t length, word32 flags) const;
 
471
 
 
472
        inline CipherDir GetCipherDirection() const {return IsForwardTransformation() ? ENCRYPTION : DECRYPTION;}
 
473
};
 
474
 
 
475
//! interface for the data processing part of stream ciphers
 
476
 
 
477
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE StreamTransformation : public Algorithm
 
478
{
 
479
public:
 
480
        //! return a reference to this object, 
 
481
        /*! This function is useful for passing a temporary StreamTransformation object to a 
 
482
                function that takes a non-const reference. */
 
483
        StreamTransformation& Ref() {return *this;}
 
484
 
 
485
        //! returns block size, if input must be processed in blocks, otherwise 1
 
486
        virtual unsigned int MandatoryBlockSize() const {return 1;}
 
487
 
 
488
        //! returns the input block size that is most efficient for this cipher
 
489
        /*! \note optimal input length is n * OptimalBlockSize() - GetOptimalBlockSizeUsed() for any n > 0 */
 
490
        virtual unsigned int OptimalBlockSize() const {return MandatoryBlockSize();}
 
491
        //! returns how much of the current block is used up
 
492
        virtual unsigned int GetOptimalBlockSizeUsed() const {return 0;}
 
493
 
 
494
        //! returns how input should be aligned for optimal performance
 
495
        virtual unsigned int OptimalDataAlignment() const;
 
496
 
 
497
        //! encrypt or decrypt an array of bytes of specified length
 
498
        /*! \note either inString == outString, or they don't overlap */
 
499
        virtual void ProcessData(byte *outString, const byte *inString, size_t length) =0;
 
500
 
 
501
        //! for ciphers where the last block of data is special, encrypt or decrypt the last block of data
 
502
        /*! For now the only use of this function is for CBC-CTS mode. */
 
503
        virtual void ProcessLastBlock(byte *outString, const byte *inString, size_t length);
 
504
        //! returns the minimum size of the last block, 0 indicating the last block is not special
 
505
        virtual unsigned int MinLastBlockSize() const {return 0;}
 
506
 
 
507
        //! same as ProcessData(inoutString, inoutString, length)
 
508
        inline void ProcessString(byte *inoutString, size_t length)
 
509
                {ProcessData(inoutString, inoutString, length);}
 
510
        //! same as ProcessData(outString, inString, length)
 
511
        inline void ProcessString(byte *outString, const byte *inString, size_t length)
 
512
                {ProcessData(outString, inString, length);}
 
513
        //! implemented as {ProcessData(&input, &input, 1); return input;}
 
514
        inline byte ProcessByte(byte input)
 
515
                {ProcessData(&input, &input, 1); return input;}
 
516
 
 
517
        //! returns whether this cipher supports random access
 
518
        virtual bool IsRandomAccess() const =0;
 
519
        //! for random access ciphers, seek to an absolute position
 
520
        virtual void Seek(lword n)
 
521
        {
 
522
                assert(!IsRandomAccess());
 
523
                throw NotImplemented("StreamTransformation: this object doesn't support random access");
 
524
        }
 
525
 
 
526
        //! returns whether this transformation is self-inverting (e.g. xor with a keystream)
 
527
        virtual bool IsSelfInverting() const =0;
 
528
        //! returns whether this is an encryption object
 
529
        virtual bool IsForwardTransformation() const =0;
 
530
};
 
531
 
 
532
//! interface for hash functions and data processing part of MACs
 
533
 
 
534
/*! HashTransformation objects are stateful.  They are created in an initial state,
 
535
        change state as Update() is called, and return to the initial
 
536
        state when Final() is called.  This interface allows a large message to
 
537
        be hashed in pieces by calling Update() on each piece followed by
 
538
        calling Final().
 
539
*/
 
540
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE HashTransformation : public Algorithm
 
541
{
 
542
public:
 
543
        //! return a reference to this object, 
 
544
        /*! This function is useful for passing a temporary HashTransformation object to a 
 
545
                function that takes a non-const reference. */
 
546
        HashTransformation& Ref() {return *this;}
 
547
 
 
548
        //! process more input
 
549
        virtual void Update(const byte *input, size_t length) =0;
 
550
 
 
551
        //! request space to write input into
 
552
        virtual byte * CreateUpdateSpace(size_t &size) {size=0; return NULL;}
 
553
 
 
554
        //! compute hash for current message, then restart for a new message
 
555
        /*!     \pre size of digest == DigestSize(). */
 
556
        virtual void Final(byte *digest)
 
557
                {TruncatedFinal(digest, DigestSize());}
 
558
 
 
559
        //! discard the current state, and restart with a new message
 
560
        virtual void Restart()
 
561
                {TruncatedFinal(NULL, 0);}
 
562
 
 
563
        //! size of the hash/digest/MAC returned by Final()
 
564
        virtual unsigned int DigestSize() const =0;
 
565
 
 
566
        //! same as DigestSize()
 
567
        unsigned int TagSize() const {return DigestSize();}
 
568
 
 
569
 
 
570
        //! block size of underlying compression function, or 0 if not block based
 
571
        virtual unsigned int BlockSize() const {return 0;}
 
572
 
 
573
        //! input to Update() should have length a multiple of this for optimal speed
 
574
        virtual unsigned int OptimalBlockSize() const {return 1;}
 
575
 
 
576
        //! returns how input should be aligned for optimal performance
 
577
        virtual unsigned int OptimalDataAlignment() const;
 
578
 
 
579
        //! use this if your input is in one piece and you don't want to call Update() and Final() separately
 
580
        virtual void CalculateDigest(byte *digest, const byte *input, size_t length)
 
581
                {Update(input, length); Final(digest);}
 
582
 
 
583
        //! verify that digest is a valid digest for the current message, then reinitialize the object
 
584
        /*! Default implementation is to call Final() and do a bitwise comparison
 
585
                between its output and digest. */
 
586
        virtual bool Verify(const byte *digest)
 
587
                {return TruncatedVerify(digest, DigestSize());}
 
588
 
 
589
        //! use this if your input is in one piece and you don't want to call Update() and Verify() separately
 
590
        virtual bool VerifyDigest(const byte *digest, const byte *input, size_t length)
 
591
                {Update(input, length); return Verify(digest);}
 
592
 
 
593
        //! truncated version of Final()
 
594
        virtual void TruncatedFinal(byte *digest, size_t digestSize) =0;
 
595
 
 
596
        //! truncated version of CalculateDigest()
 
597
        virtual void CalculateTruncatedDigest(byte *digest, size_t digestSize, const byte *input, size_t length)
 
598
                {Update(input, length); TruncatedFinal(digest, digestSize);}
 
599
 
 
600
        //! truncated version of Verify()
 
601
        virtual bool TruncatedVerify(const byte *digest, size_t digestLength);
 
602
 
 
603
        //! truncated version of VerifyDigest()
 
604
        virtual bool VerifyTruncatedDigest(const byte *digest, size_t digestLength, const byte *input, size_t length)
 
605
                {Update(input, length); return TruncatedVerify(digest, digestLength);}
 
606
 
 
607
protected:
 
608
        void ThrowIfInvalidTruncatedSize(size_t size) const;
 
609
};
 
610
 
 
611
typedef HashTransformation HashFunction;
 
612
 
 
613
//! interface for one direction (encryption or decryption) of a block cipher
 
614
/*! \note These objects usually should not be used directly. See BlockTransformation for more details. */
 
615
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE BlockCipher : public SimpleKeyingInterface, public BlockTransformation
 
616
{
 
617
protected:
 
618
        const Algorithm & GetAlgorithm() const {return *this;}
 
619
};
 
620
 
 
621
//! interface for one direction (encryption or decryption) of a stream cipher or cipher mode
 
622
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE SymmetricCipher : public SimpleKeyingInterface, public StreamTransformation
 
623
{
 
624
protected:
 
625
        const Algorithm & GetAlgorithm() const {return *this;}
 
626
};
 
627
 
 
628
//! interface for message authentication codes
 
629
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE MessageAuthenticationCode : public SimpleKeyingInterface, public HashTransformation
 
630
{
 
631
protected:
 
632
        const Algorithm & GetAlgorithm() const {return *this;}
 
633
};
 
634
 
 
635
//! interface for for one direction (encryption or decryption) of a stream cipher or block cipher mode with authentication
 
636
/*! The StreamTransformation part of this interface is used to encrypt/decrypt the data, and the MessageAuthenticationCode part of this
 
637
        interface is used to input additional authenticated data (AAD, which is MAC'ed but not encrypted), and to generate/verify the MAC. */
 
638
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE AuthenticatedSymmetricCipher : public MessageAuthenticationCode, public StreamTransformation
 
639
{
 
640
public:
 
641
        //! this indicates that a member function was called in the wrong state, for example trying to encrypt a message before having set the key or IV
 
642
        class BadState : public Exception
 
643
        {
 
644
        public:
 
645
                explicit BadState(const std::string &name, const char *message) : Exception(OTHER_ERROR, name + ": " + message) {}
 
646
                explicit BadState(const std::string &name, const char *function, const char *state) : Exception(OTHER_ERROR, name + ": " + function + " was called before " + state) {}
 
647
        };
 
648
 
 
649
        //! the maximum length of AAD that can be input before the encrypted data
 
650
        virtual lword MaxHeaderLength() const =0;
 
651
        //! the maximum length of encrypted data
 
652
        virtual lword MaxMessageLength() const =0;
 
653
        //! the maximum length of AAD that can be input after the encrypted data
 
654
        virtual lword MaxFooterLength() const {return 0;}
 
655
        //! if this function returns true, SpecifyDataLengths() must be called before attempting to input data
 
656
        /*! This is the case for some schemes, such as CCM. */
 
657
        virtual bool NeedsPrespecifiedDataLengths() const {return false;}
 
658
        //! this function only needs to be called if NeedsPrespecifiedDataLengths() returns true
 
659
        void SpecifyDataLengths(lword headerLength, lword messageLength, lword footerLength=0);
 
660
        //! encrypt and generate MAC in one call. will truncate MAC if macSize < TagSize()
 
661
        virtual void EncryptAndAuthenticate(byte *ciphertext, byte *mac, size_t macSize, const byte *iv, int ivLength, const byte *header, size_t headerLength, const byte *message, size_t messageLength);
 
662
        //! decrypt and verify MAC in one call, returning true iff MAC is valid. will assume MAC is truncated if macLength < TagSize()
 
663
        virtual bool DecryptAndVerify(byte *message, const byte *mac, size_t macLength, const byte *iv, int ivLength, const byte *header, size_t headerLength, const byte *ciphertext, size_t ciphertextLength);
 
664
 
 
665
        // redeclare this to avoid compiler ambiguity errors
 
666
        virtual std::string AlgorithmName() const =0;
 
667
 
 
668
protected:
 
669
        const Algorithm & GetAlgorithm() const {return *static_cast<const MessageAuthenticationCode *>(this);}
 
670
        virtual void UncheckedSpecifyDataLengths(lword headerLength, lword messageLength, lword footerLength) {}
 
671
};
 
672
 
 
673
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
674
typedef SymmetricCipher StreamCipher;
 
675
#endif
 
676
 
 
677
//! interface for random number generators
 
678
/*! All return values are uniformly distributed over the range specified.
 
679
*/
 
680
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE RandomNumberGenerator : public Algorithm
 
681
{
 
682
public:
 
683
        //! update RNG state with additional unpredictable values
 
684
        virtual void IncorporateEntropy(const byte *input, size_t length) {throw NotImplemented("RandomNumberGenerator: IncorporateEntropy not implemented");}
 
685
 
 
686
        //! returns true if IncorporateEntropy is implemented
 
687
        virtual bool CanIncorporateEntropy() const {return false;}
 
688
 
 
689
        //! generate new random byte and return it
 
690
        virtual byte GenerateByte();
 
691
 
 
692
        //! generate new random bit and return it
 
693
        /*! Default implementation is to call GenerateByte() and return its lowest bit. */
 
694
        virtual unsigned int GenerateBit();
 
695
 
 
696
        //! generate a random 32 bit word in the range min to max, inclusive
 
697
        virtual word32 GenerateWord32(word32 a=0, word32 b=0xffffffffL);
 
698
 
 
699
        //! generate random array of bytes
 
700
        virtual void GenerateBlock(byte *output, size_t size);
 
701
 
 
702
        //! generate and discard n bytes
 
703
        virtual void DiscardBytes(size_t n);
 
704
 
 
705
        //! generate random bytes as input to a BufferedTransformation
 
706
        virtual void GenerateIntoBufferedTransformation(BufferedTransformation &target, const std::string &channel, lword length);
 
707
 
 
708
        //! randomly shuffle the specified array, resulting permutation is uniformly distributed
 
709
        template <class IT> void Shuffle(IT begin, IT end)
 
710
        {
 
711
                for (; begin != end; ++begin)
 
712
                        std::iter_swap(begin, begin + GenerateWord32(0, end-begin-1));
 
713
        }
 
714
 
 
715
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
716
        byte GetByte() {return GenerateByte();}
 
717
        unsigned int GetBit() {return GenerateBit();}
 
718
        word32 GetLong(word32 a=0, word32 b=0xffffffffL) {return GenerateWord32(a, b);}
 
719
        word16 GetShort(word16 a=0, word16 b=0xffff) {return (word16)GenerateWord32(a, b);}
 
720
        void GetBlock(byte *output, size_t size) {GenerateBlock(output, size);}
 
721
#endif
 
722
};
 
723
 
 
724
//! returns a reference that can be passed to functions that ask for a RNG but doesn't actually use it
 
725
CRYPTOPP_DLL RandomNumberGenerator & CRYPTOPP_API NullRNG();
 
726
 
 
727
class WaitObjectContainer;
 
728
class CallStack;
 
729
 
 
730
//! interface for objects that you can wait for
 
731
 
 
732
class CRYPTOPP_NO_VTABLE Waitable
 
733
{
 
734
public:
 
735
        virtual ~Waitable() {}
 
736
 
 
737
        //! maximum number of wait objects that this object can return
 
738
        virtual unsigned int GetMaxWaitObjectCount() const =0;
 
739
        //! put wait objects into container
 
740
        /*! \param callStack is used for tracing no wait loops, example:
 
741
                     something.GetWaitObjects(c, CallStack("my func after X", 0));
 
742
                           - or in an outer GetWaitObjects() method that itself takes a callStack parameter:
 
743
                             innerThing.GetWaitObjects(c, CallStack("MyClass::GetWaitObjects at X", &callStack)); */
 
744
        virtual void GetWaitObjects(WaitObjectContainer &container, CallStack const& callStack) =0;
 
745
        //! wait on this object
 
746
        /*! same as creating an empty container, calling GetWaitObjects(), and calling Wait() on the container */
 
747
        bool Wait(unsigned long milliseconds, CallStack const& callStack);
 
748
};
 
749
 
 
750
//! the default channel for BufferedTransformation, equal to the empty string
 
751
extern CRYPTOPP_DLL const std::string DEFAULT_CHANNEL;
 
752
 
 
753
//! channel for additional authenticated data, equal to "AAD"
 
754
extern CRYPTOPP_DLL const std::string AAD_CHANNEL;
 
755
 
 
756
//! interface for buffered transformations
 
757
 
 
758
/*! BufferedTransformation is a generalization of BlockTransformation,
 
759
        StreamTransformation, and HashTransformation.
 
760
 
 
761
        A buffered transformation is an object that takes a stream of bytes
 
762
        as input (this may be done in stages), does some computation on them, and
 
763
        then places the result into an internal buffer for later retrieval.  Any
 
764
        partial result already in the output buffer is not modified by further
 
765
        input.
 
766
 
 
767
        If a method takes a "blocking" parameter, and you
 
768
        pass "false" for it, the method will return before all input has been processed if
 
769
        the input cannot be processed without waiting (for network buffers to become available, for example).
 
770
        In this case the method will return true
 
771
        or a non-zero integer value. When this happens you must continue to call the method with the same
 
772
        parameters until it returns false or zero, before calling any other method on it or
 
773
        attached BufferedTransformation. The integer return value in this case is approximately
 
774
        the number of bytes left to be processed, and can be used to implement a progress bar.
 
775
 
 
776
        For functions that take a "propagation" parameter, propagation != 0 means pass on the signal to attached
 
777
        BufferedTransformation objects, with propagation decremented at each step until it reaches 0.
 
778
        -1 means unlimited propagation.
 
779
 
 
780
        \nosubgrouping
 
781
*/
 
782
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE BufferedTransformation : public Algorithm, public Waitable
 
783
{
 
784
public:
 
785
        // placed up here for CW8
 
786
        static const std::string &NULL_CHANNEL; // same as DEFAULT_CHANNEL, for backwards compatibility
 
787
 
 
788
        BufferedTransformation() : Algorithm(false) {}
 
789
 
 
790
        //! return a reference to this object
 
791
        /*! This function is useful for passing a temporary BufferedTransformation object to a 
 
792
                function that takes a non-const reference. */
 
793
        BufferedTransformation& Ref() {return *this;}
 
794
 
 
795
        //!     \name INPUT
 
796
        //@{
 
797
                //! input a byte for processing
 
798
                size_t Put(byte inByte, bool blocking=true)
 
799
                        {return Put(&inByte, 1, blocking);}
 
800
                //! input multiple bytes
 
801
                size_t Put(const byte *inString, size_t length, bool blocking=true)
 
802
                        {return Put2(inString, length, 0, blocking);}
 
803
 
 
804
                //! input a 16-bit word
 
805
                size_t PutWord16(word16 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
 
806
                //! input a 32-bit word
 
807
                size_t PutWord32(word32 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
 
808
 
 
809
                //! request space which can be written into by the caller, and then used as input to Put()
 
810
                /*! \param size is requested size (as a hint) for input, and size of the returned space for output */
 
811
                /*! \note The purpose of this method is to help avoid doing extra memory allocations. */
 
812
                virtual byte * CreatePutSpace(size_t &size) {size=0; return NULL;}
 
813
 
 
814
                virtual bool CanModifyInput() const {return false;}
 
815
 
 
816
                //! input multiple bytes that may be modified by callee
 
817
                size_t PutModifiable(byte *inString, size_t length, bool blocking=true)
 
818
                        {return PutModifiable2(inString, length, 0, blocking);}
 
819
 
 
820
                bool MessageEnd(int propagation=-1, bool blocking=true)
 
821
                        {return !!Put2(NULL, 0, propagation < 0 ? -1 : propagation+1, blocking);}
 
822
                size_t PutMessageEnd(const byte *inString, size_t length, int propagation=-1, bool blocking=true)
 
823
                        {return Put2(inString, length, propagation < 0 ? -1 : propagation+1, blocking);}
 
824
 
 
825
                //! input multiple bytes for blocking or non-blocking processing
 
826
                /*! \param messageEnd means how many filters to signal MessageEnd to, including this one */
 
827
                virtual size_t Put2(const byte *inString, size_t length, int messageEnd, bool blocking) =0;
 
828
                //! input multiple bytes that may be modified by callee for blocking or non-blocking processing
 
829
                /*! \param messageEnd means how many filters to signal MessageEnd to, including this one */
 
830
                virtual size_t PutModifiable2(byte *inString, size_t length, int messageEnd, bool blocking)
 
831
                        {return Put2(inString, length, messageEnd, blocking);}
 
832
 
 
833
                //! thrown by objects that have not implemented nonblocking input processing
 
834
                struct BlockingInputOnly : public NotImplemented
 
835
                        {BlockingInputOnly(const std::string &s) : NotImplemented(s + ": Nonblocking input is not implemented by this object.") {}};
 
836
        //@}
 
837
 
 
838
        //!     \name WAITING
 
839
        //@{
 
840
                unsigned int GetMaxWaitObjectCount() const;
 
841
                void GetWaitObjects(WaitObjectContainer &container, CallStack const& callStack);
 
842
        //@}
 
843
 
 
844
        //!     \name SIGNALS
 
845
        //@{
 
846
                virtual void IsolatedInitialize(const NameValuePairs &parameters) {throw NotImplemented("BufferedTransformation: this object can't be reinitialized");}
 
847
                virtual bool IsolatedFlush(bool hardFlush, bool blocking) =0;
 
848
                virtual bool IsolatedMessageSeriesEnd(bool blocking) {return false;}
 
849
 
 
850
                //! initialize or reinitialize this object
 
851
                virtual void Initialize(const NameValuePairs &parameters=g_nullNameValuePairs, int propagation=-1);
 
852
                //! flush buffered input and/or output
 
853
                /*! \param hardFlush is used to indicate whether all data should be flushed
 
854
                        \note Hard flushes must be used with care. It means try to process and output everything, even if
 
855
                        there may not be enough data to complete the action. For example, hard flushing a HexDecoder would
 
856
                        cause an error if you do it after inputing an odd number of hex encoded characters.
 
857
                        For some types of filters, for example ZlibDecompressor, hard flushes can only
 
858
                        be done at "synchronization points". These synchronization points are positions in the data
 
859
                        stream that are created by hard flushes on the corresponding reverse filters, in this
 
860
                        example ZlibCompressor. This is useful when zlib compressed data is moved across a
 
861
                        network in packets and compression state is preserved across packets, as in the ssh2 protocol.
 
862
                */
 
863
                virtual bool Flush(bool hardFlush, int propagation=-1, bool blocking=true);
 
864
                //! mark end of a series of messages
 
865
                /*! There should be a MessageEnd immediately before MessageSeriesEnd. */
 
866
                virtual bool MessageSeriesEnd(int propagation=-1, bool blocking=true);
 
867
 
 
868
                //! set propagation of automatically generated and transferred signals
 
869
                /*! propagation == 0 means do not automaticly generate signals */
 
870
                virtual void SetAutoSignalPropagation(int propagation) {}
 
871
 
 
872
                //!
 
873
                virtual int GetAutoSignalPropagation() const {return 0;}
 
874
public:
 
875
 
 
876
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
877
                void Close() {MessageEnd();}
 
878
#endif
 
879
        //@}
 
880
 
 
881
        //!     \name RETRIEVAL OF ONE MESSAGE
 
882
        //@{
 
883
                //! returns number of bytes that is currently ready for retrieval
 
884
                /*! All retrieval functions return the actual number of bytes
 
885
                        retrieved, which is the lesser of the request number and
 
886
                        MaxRetrievable(). */
 
887
                virtual lword MaxRetrievable() const;
 
888
 
 
889
                //! returns whether any bytes are currently ready for retrieval
 
890
                virtual bool AnyRetrievable() const;
 
891
 
 
892
                //! try to retrieve a single byte
 
893
                virtual size_t Get(byte &outByte);
 
894
                //! try to retrieve multiple bytes
 
895
                virtual size_t Get(byte *outString, size_t getMax);
 
896
 
 
897
                //! peek at the next byte without removing it from the output buffer
 
898
                virtual size_t Peek(byte &outByte) const;
 
899
                //! peek at multiple bytes without removing them from the output buffer
 
900
                virtual size_t Peek(byte *outString, size_t peekMax) const;
 
901
 
 
902
                //! try to retrieve a 16-bit word
 
903
                size_t GetWord16(word16 &value, ByteOrder order=BIG_ENDIAN_ORDER);
 
904
                //! try to retrieve a 32-bit word
 
905
                size_t GetWord32(word32 &value, ByteOrder order=BIG_ENDIAN_ORDER);
 
906
 
 
907
                //! try to peek at a 16-bit word
 
908
                size_t PeekWord16(word16 &value, ByteOrder order=BIG_ENDIAN_ORDER) const;
 
909
                //! try to peek at a 32-bit word
 
910
                size_t PeekWord32(word32 &value, ByteOrder order=BIG_ENDIAN_ORDER) const;
 
911
 
 
912
                //! move transferMax bytes of the buffered output to target as input
 
913
                lword TransferTo(BufferedTransformation &target, lword transferMax=LWORD_MAX, const std::string &channel=DEFAULT_CHANNEL)
 
914
                        {TransferTo2(target, transferMax, channel); return transferMax;}
 
915
 
 
916
                //! discard skipMax bytes from the output buffer
 
917
                virtual lword Skip(lword skipMax=LWORD_MAX);
 
918
 
 
919
                //! copy copyMax bytes of the buffered output to target as input
 
920
                lword CopyTo(BufferedTransformation &target, lword copyMax=LWORD_MAX, const std::string &channel=DEFAULT_CHANNEL) const
 
921
                        {return CopyRangeTo(target, 0, copyMax, channel);}
 
922
 
 
923
                //! copy copyMax bytes of the buffered output, starting at position (relative to current position), to target as input
 
924
                lword CopyRangeTo(BufferedTransformation &target, lword position, lword copyMax=LWORD_MAX, const std::string &channel=DEFAULT_CHANNEL) const
 
925
                        {lword i = position; CopyRangeTo2(target, i, i+copyMax, channel); return i-position;}
 
926
 
 
927
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
928
                unsigned long MaxRetrieveable() const {return MaxRetrievable();}
 
929
#endif
 
930
        //@}
 
931
 
 
932
        //!     \name RETRIEVAL OF MULTIPLE MESSAGES
 
933
        //@{
 
934
                //!
 
935
                virtual lword TotalBytesRetrievable() const;
 
936
                //! number of times MessageEnd() has been received minus messages retrieved or skipped
 
937
                virtual unsigned int NumberOfMessages() const;
 
938
                //! returns true if NumberOfMessages() > 0
 
939
                virtual bool AnyMessages() const;
 
940
                //! start retrieving the next message
 
941
                /*!
 
942
                        Returns false if no more messages exist or this message 
 
943
                        is not completely retrieved.
 
944
                */
 
945
                virtual bool GetNextMessage();
 
946
                //! skip count number of messages
 
947
                virtual unsigned int SkipMessages(unsigned int count=UINT_MAX);
 
948
                //!
 
949
                unsigned int TransferMessagesTo(BufferedTransformation &target, unsigned int count=UINT_MAX, const std::string &channel=DEFAULT_CHANNEL)
 
950
                        {TransferMessagesTo2(target, count, channel); return count;}
 
951
                //!
 
952
                unsigned int CopyMessagesTo(BufferedTransformation &target, unsigned int count=UINT_MAX, const std::string &channel=DEFAULT_CHANNEL) const;
 
953
 
 
954
                //!
 
955
                virtual void SkipAll();
 
956
                //!
 
957
                void TransferAllTo(BufferedTransformation &target, const std::string &channel=DEFAULT_CHANNEL)
 
958
                        {TransferAllTo2(target, channel);}
 
959
                //!
 
960
                void CopyAllTo(BufferedTransformation &target, const std::string &channel=DEFAULT_CHANNEL) const;
 
961
 
 
962
                virtual bool GetNextMessageSeries() {return false;}
 
963
                virtual unsigned int NumberOfMessagesInThisSeries() const {return NumberOfMessages();}
 
964
                virtual unsigned int NumberOfMessageSeries() const {return 0;}
 
965
        //@}
 
966
 
 
967
        //!     \name NON-BLOCKING TRANSFER OF OUTPUT
 
968
        //@{
 
969
                //! upon return, byteCount contains number of bytes that have finished being transfered, and returns the number of bytes left in the current transfer block
 
970
                virtual size_t TransferTo2(BufferedTransformation &target, lword &byteCount, const std::string &channel=DEFAULT_CHANNEL, bool blocking=true) =0;
 
971
                //! upon return, begin contains the start position of data yet to be finished copying, and returns the number of bytes left in the current transfer block
 
972
                virtual size_t CopyRangeTo2(BufferedTransformation &target, lword &begin, lword end=LWORD_MAX, const std::string &channel=DEFAULT_CHANNEL, bool blocking=true) const =0;
 
973
                //! upon return, messageCount contains number of messages that have finished being transfered, and returns the number of bytes left in the current transfer block
 
974
                size_t TransferMessagesTo2(BufferedTransformation &target, unsigned int &messageCount, const std::string &channel=DEFAULT_CHANNEL, bool blocking=true);
 
975
                //! returns the number of bytes left in the current transfer block
 
976
                size_t TransferAllTo2(BufferedTransformation &target, const std::string &channel=DEFAULT_CHANNEL, bool blocking=true);
 
977
        //@}
 
978
 
 
979
        //!     \name CHANNELS
 
980
        //@{
 
981
                struct NoChannelSupport : public NotImplemented
 
982
                        {NoChannelSupport(const std::string &name) : NotImplemented(name + ": this object doesn't support multiple channels") {}};
 
983
                struct InvalidChannelName : public InvalidArgument
 
984
                        {InvalidChannelName(const std::string &name, const std::string &channel) : InvalidArgument(name + ": unexpected channel name \"" + channel + "\"") {}};
 
985
 
 
986
                size_t ChannelPut(const std::string &channel, byte inByte, bool blocking=true)
 
987
                        {return ChannelPut(channel, &inByte, 1, blocking);}
 
988
                size_t ChannelPut(const std::string &channel, const byte *inString, size_t length, bool blocking=true)
 
989
                        {return ChannelPut2(channel, inString, length, 0, blocking);}
 
990
 
 
991
                size_t ChannelPutModifiable(const std::string &channel, byte *inString, size_t length, bool blocking=true)
 
992
                        {return ChannelPutModifiable2(channel, inString, length, 0, blocking);}
 
993
 
 
994
                size_t ChannelPutWord16(const std::string &channel, word16 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
 
995
                size_t ChannelPutWord32(const std::string &channel, word32 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
 
996
 
 
997
                bool ChannelMessageEnd(const std::string &channel, int propagation=-1, bool blocking=true)
 
998
                        {return !!ChannelPut2(channel, NULL, 0, propagation < 0 ? -1 : propagation+1, blocking);}
 
999
                size_t ChannelPutMessageEnd(const std::string &channel, const byte *inString, size_t length, int propagation=-1, bool blocking=true)
 
1000
                        {return ChannelPut2(channel, inString, length, propagation < 0 ? -1 : propagation+1, blocking);}
 
1001
 
 
1002
                virtual byte * ChannelCreatePutSpace(const std::string &channel, size_t &size);
 
1003
 
 
1004
                virtual size_t ChannelPut2(const std::string &channel, const byte *begin, size_t length, int messageEnd, bool blocking);
 
1005
                virtual size_t ChannelPutModifiable2(const std::string &channel, byte *begin, size_t length, int messageEnd, bool blocking);
 
1006
 
 
1007
                virtual bool ChannelFlush(const std::string &channel, bool hardFlush, int propagation=-1, bool blocking=true);
 
1008
                virtual bool ChannelMessageSeriesEnd(const std::string &channel, int propagation=-1, bool blocking=true);
 
1009
 
 
1010
                virtual void SetRetrievalChannel(const std::string &channel);
 
1011
        //@}
 
1012
 
 
1013
        //!     \name ATTACHMENT
 
1014
        /*! Some BufferedTransformation objects (e.g. Filter objects)
 
1015
                allow other BufferedTransformation objects to be attached. When
 
1016
                this is done, the first object instead of buffering its output,
 
1017
                sents that output to the attached object as input. The entire
 
1018
                attachment chain is deleted when the anchor object is destructed.
 
1019
        */
 
1020
        //@{
 
1021
                //! returns whether this object allows attachment
 
1022
                virtual bool Attachable() {return false;}
 
1023
                //! returns the object immediately attached to this object or NULL for no attachment
 
1024
                virtual BufferedTransformation *AttachedTransformation() {assert(!Attachable()); return 0;}
 
1025
                //!
 
1026
                virtual const BufferedTransformation *AttachedTransformation() const
 
1027
                        {return const_cast<BufferedTransformation *>(this)->AttachedTransformation();}
 
1028
                //! delete the current attachment chain and replace it with newAttachment
 
1029
                virtual void Detach(BufferedTransformation *newAttachment = 0)
 
1030
                        {assert(!Attachable()); throw NotImplemented("BufferedTransformation: this object is not attachable");}
 
1031
                //! add newAttachment to the end of attachment chain
 
1032
                virtual void Attach(BufferedTransformation *newAttachment);
 
1033
        //@}
 
1034
 
 
1035
protected:
 
1036
        static int DecrementPropagation(int propagation)
 
1037
                {return propagation != 0 ? propagation - 1 : 0;}
 
1038
 
 
1039
private:
 
1040
        byte m_buf[4];  // for ChannelPutWord16 and ChannelPutWord32, to ensure buffer isn't deallocated before non-blocking operation completes
 
1041
};
 
1042
 
 
1043
//! returns a reference to a BufferedTransformation object that discards all input
 
1044
BufferedTransformation & TheBitBucket();
 
1045
 
 
1046
//! interface for crypto material, such as public and private keys, and crypto parameters
 
1047
 
 
1048
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE CryptoMaterial : public NameValuePairs
 
1049
{
 
1050
public:
 
1051
        //! exception thrown when invalid crypto material is detected
 
1052
        class CRYPTOPP_DLL InvalidMaterial : public InvalidDataFormat
 
1053
        {
 
1054
        public:
 
1055
                explicit InvalidMaterial(const std::string &s) : InvalidDataFormat(s) {}
 
1056
        };
 
1057
 
 
1058
        //! assign values from source to this object
 
1059
        /*! \note This function can be used to create a public key from a private key. */
 
1060
        virtual void AssignFrom(const NameValuePairs &source) =0;
 
1061
 
 
1062
        //! check this object for errors
 
1063
        /*! \param level denotes the level of thoroughness:
 
1064
                0 - using this object won't cause a crash or exception (rng is ignored)
 
1065
                1 - this object will probably function (encrypt, sign, etc.) correctly (but may not check for weak keys and such)
 
1066
                2 - make sure this object will function correctly, and do reasonable security checks
 
1067
                3 - do checks that may take a long time
 
1068
                \return true if the tests pass */
 
1069
        virtual bool Validate(RandomNumberGenerator &rng, unsigned int level) const =0;
 
1070
 
 
1071
        //! throws InvalidMaterial if this object fails Validate() test
 
1072
        virtual void ThrowIfInvalid(RandomNumberGenerator &rng, unsigned int level) const
 
1073
                {if (!Validate(rng, level)) throw InvalidMaterial("CryptoMaterial: this object contains invalid values");}
 
1074
 
 
1075
//      virtual std::vector<std::string> GetSupportedFormats(bool includeSaveOnly=false, bool includeLoadOnly=false);
 
1076
 
 
1077
        //! save key into a BufferedTransformation
 
1078
        virtual void Save(BufferedTransformation &bt) const
 
1079
                {throw NotImplemented("CryptoMaterial: this object does not support saving");}
 
1080
 
 
1081
        //! load key from a BufferedTransformation
 
1082
        /*! \throws KeyingErr if decode fails
 
1083
                \note Generally does not check that the key is valid.
 
1084
                        Call ValidateKey() or ThrowIfInvalidKey() to check that. */
 
1085
        virtual void Load(BufferedTransformation &bt)
 
1086
                {throw NotImplemented("CryptoMaterial: this object does not support loading");}
 
1087
 
 
1088
        //! \return whether this object supports precomputation
 
1089
        virtual bool SupportsPrecomputation() const {return false;}
 
1090
        //! do precomputation
 
1091
        /*! The exact semantics of Precompute() is varies, but
 
1092
                typically it means calculate a table of n objects
 
1093
                that can be used later to speed up computation. */
 
1094
        virtual void Precompute(unsigned int n)
 
1095
                {assert(!SupportsPrecomputation()); throw NotImplemented("CryptoMaterial: this object does not support precomputation");}
 
1096
        //! retrieve previously saved precomputation
 
1097
        virtual void LoadPrecomputation(BufferedTransformation &storedPrecomputation)
 
1098
                {assert(!SupportsPrecomputation()); throw NotImplemented("CryptoMaterial: this object does not support precomputation");}
 
1099
        //! save precomputation for later use
 
1100
        virtual void SavePrecomputation(BufferedTransformation &storedPrecomputation) const
 
1101
                {assert(!SupportsPrecomputation()); throw NotImplemented("CryptoMaterial: this object does not support precomputation");}
 
1102
 
 
1103
        // for internal library use
 
1104
        void DoQuickSanityCheck() const {ThrowIfInvalid(NullRNG(), 0);}
 
1105
 
 
1106
#if (defined(__SUNPRO_CC) && __SUNPRO_CC < 0x590)
 
1107
        // Sun Studio 11/CC 5.8 workaround: it generates incorrect code when casting to an empty virtual base class
 
1108
        char m_sunCCworkaround;
 
1109
#endif
 
1110
};
 
1111
 
 
1112
//! interface for generatable crypto material, such as private keys and crypto parameters
 
1113
 
 
1114
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE GeneratableCryptoMaterial : virtual public CryptoMaterial
 
1115
{
 
1116
public:
 
1117
        //! generate a random key or crypto parameters
 
1118
        /*! \throws KeyingErr if algorithm parameters are invalid, or if a key can't be generated
 
1119
                (e.g., if this is a public key object) */
 
1120
        virtual void GenerateRandom(RandomNumberGenerator &rng, const NameValuePairs &params = g_nullNameValuePairs)
 
1121
                {throw NotImplemented("GeneratableCryptoMaterial: this object does not support key/parameter generation");}
 
1122
 
 
1123
        //! calls the above function with a NameValuePairs object that just specifies "KeySize"
 
1124
        void GenerateRandomWithKeySize(RandomNumberGenerator &rng, unsigned int keySize);
 
1125
};
 
1126
 
 
1127
//! interface for public keys
 
1128
 
 
1129
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PublicKey : virtual public CryptoMaterial
 
1130
{
 
1131
};
 
1132
 
 
1133
//! interface for private keys
 
1134
 
 
1135
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PrivateKey : public GeneratableCryptoMaterial
 
1136
{
 
1137
};
 
1138
 
 
1139
//! interface for crypto prameters
 
1140
 
 
1141
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE CryptoParameters : public GeneratableCryptoMaterial
 
1142
{
 
1143
};
 
1144
 
 
1145
//! interface for asymmetric algorithms
 
1146
 
 
1147
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE AsymmetricAlgorithm : public Algorithm
 
1148
{
 
1149
public:
 
1150
        //! returns a reference to the crypto material used by this object
 
1151
        virtual CryptoMaterial & AccessMaterial() =0;
 
1152
        //! returns a const reference to the crypto material used by this object
 
1153
        virtual const CryptoMaterial & GetMaterial() const =0;
 
1154
 
 
1155
        //! for backwards compatibility, calls AccessMaterial().Load(bt)
 
1156
        void BERDecode(BufferedTransformation &bt)
 
1157
                {AccessMaterial().Load(bt);}
 
1158
        //! for backwards compatibility, calls GetMaterial().Save(bt)
 
1159
        void DEREncode(BufferedTransformation &bt) const
 
1160
                {GetMaterial().Save(bt);}
 
1161
};
 
1162
 
 
1163
//! interface for asymmetric algorithms using public keys
 
1164
 
 
1165
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PublicKeyAlgorithm : public AsymmetricAlgorithm
 
1166
{
 
1167
public:
 
1168
        // VC60 workaround: no co-variant return type
 
1169
        CryptoMaterial & AccessMaterial() {return AccessPublicKey();}
 
1170
        const CryptoMaterial & GetMaterial() const {return GetPublicKey();}
 
1171
 
 
1172
        virtual PublicKey & AccessPublicKey() =0;
 
1173
        virtual const PublicKey & GetPublicKey() const {return const_cast<PublicKeyAlgorithm *>(this)->AccessPublicKey();}
 
1174
};
 
1175
 
 
1176
//! interface for asymmetric algorithms using private keys
 
1177
 
 
1178
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PrivateKeyAlgorithm : public AsymmetricAlgorithm
 
1179
{
 
1180
public:
 
1181
        CryptoMaterial & AccessMaterial() {return AccessPrivateKey();}
 
1182
        const CryptoMaterial & GetMaterial() const {return GetPrivateKey();}
 
1183
 
 
1184
        virtual PrivateKey & AccessPrivateKey() =0;
 
1185
        virtual const PrivateKey & GetPrivateKey() const {return const_cast<PrivateKeyAlgorithm *>(this)->AccessPrivateKey();}
 
1186
};
 
1187
 
 
1188
//! interface for key agreement algorithms
 
1189
 
 
1190
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE KeyAgreementAlgorithm : public AsymmetricAlgorithm
 
1191
{
 
1192
public:
 
1193
        CryptoMaterial & AccessMaterial() {return AccessCryptoParameters();}
 
1194
        const CryptoMaterial & GetMaterial() const {return GetCryptoParameters();}
 
1195
 
 
1196
        virtual CryptoParameters & AccessCryptoParameters() =0;
 
1197
        virtual const CryptoParameters & GetCryptoParameters() const {return const_cast<KeyAgreementAlgorithm *>(this)->AccessCryptoParameters();}
 
1198
};
 
1199
 
 
1200
//! interface for public-key encryptors and decryptors
 
1201
 
 
1202
/*! This class provides an interface common to encryptors and decryptors
 
1203
        for querying their plaintext and ciphertext lengths.
 
1204
*/
 
1205
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_CryptoSystem
 
1206
{
 
1207
public:
 
1208
        virtual ~PK_CryptoSystem() {}
 
1209
 
 
1210
        //! maximum length of plaintext for a given ciphertext length
 
1211
        /*! \note This function returns 0 if ciphertextLength is not valid (too long or too short). */
 
1212
        virtual size_t MaxPlaintextLength(size_t ciphertextLength) const =0;
 
1213
 
 
1214
        //! calculate length of ciphertext given length of plaintext
 
1215
        /*! \note This function returns 0 if plaintextLength is not valid (too long). */
 
1216
        virtual size_t CiphertextLength(size_t plaintextLength) const =0;
 
1217
 
 
1218
        //! this object supports the use of the parameter with the given name
 
1219
        /*! some possible parameter names: EncodingParameters, KeyDerivationParameters */
 
1220
        virtual bool ParameterSupported(const char *name) const =0;
 
1221
 
 
1222
        //! return fixed ciphertext length, if one exists, otherwise return 0
 
1223
        /*! \note "Fixed" here means length of ciphertext does not depend on length of plaintext.
 
1224
                It usually does depend on the key length. */
 
1225
        virtual size_t FixedCiphertextLength() const {return 0;}
 
1226
 
 
1227
        //! return maximum plaintext length given the fixed ciphertext length, if one exists, otherwise return 0
 
1228
        virtual size_t FixedMaxPlaintextLength() const {return 0;}
 
1229
 
 
1230
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
1231
        size_t MaxPlainTextLength(size_t cipherTextLength) const {return MaxPlaintextLength(cipherTextLength);}
 
1232
        size_t CipherTextLength(size_t plainTextLength) const {return CiphertextLength(plainTextLength);}
 
1233
#endif
 
1234
};
 
1235
 
 
1236
//! interface for public-key encryptors
 
1237
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Encryptor : public PK_CryptoSystem, public PublicKeyAlgorithm
 
1238
{
 
1239
public:
 
1240
        //! exception thrown when trying to encrypt plaintext of invalid length
 
1241
        class CRYPTOPP_DLL InvalidPlaintextLength : public Exception
 
1242
        {
 
1243
        public:
 
1244
                InvalidPlaintextLength() : Exception(OTHER_ERROR, "PK_Encryptor: invalid plaintext length") {}
 
1245
        };
 
1246
 
 
1247
        //! encrypt a byte string
 
1248
        /*! \pre CiphertextLength(plaintextLength) != 0 (i.e., plaintext isn't too long)
 
1249
                \pre size of ciphertext == CiphertextLength(plaintextLength)
 
1250
        */
 
1251
        virtual void Encrypt(RandomNumberGenerator &rng, 
 
1252
                const byte *plaintext, size_t plaintextLength, 
 
1253
                byte *ciphertext, const NameValuePairs &parameters = g_nullNameValuePairs) const =0;
 
1254
 
 
1255
        //! create a new encryption filter
 
1256
        /*! \note The caller is responsible for deleting the returned pointer.
 
1257
                \note Encoding parameters should be passed in the "EP" channel.
 
1258
        */
 
1259
        virtual BufferedTransformation * CreateEncryptionFilter(RandomNumberGenerator &rng, 
 
1260
                BufferedTransformation *attachment=NULL, const NameValuePairs &parameters = g_nullNameValuePairs) const;
 
1261
};
 
1262
 
 
1263
//! interface for public-key decryptors
 
1264
 
 
1265
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Decryptor : public PK_CryptoSystem, public PrivateKeyAlgorithm
 
1266
{
 
1267
public:
 
1268
        //! decrypt a byte string, and return the length of plaintext
 
1269
        /*! \pre size of plaintext == MaxPlaintextLength(ciphertextLength) bytes.
 
1270
                \return the actual length of the plaintext, indication that decryption failed.
 
1271
        */
 
1272
        virtual DecodingResult Decrypt(RandomNumberGenerator &rng, 
 
1273
                const byte *ciphertext, size_t ciphertextLength, 
 
1274
                byte *plaintext, const NameValuePairs &parameters = g_nullNameValuePairs) const =0;
 
1275
 
 
1276
        //! create a new decryption filter
 
1277
        /*! \note caller is responsible for deleting the returned pointer
 
1278
        */
 
1279
        virtual BufferedTransformation * CreateDecryptionFilter(RandomNumberGenerator &rng, 
 
1280
                BufferedTransformation *attachment=NULL, const NameValuePairs &parameters = g_nullNameValuePairs) const;
 
1281
 
 
1282
        //! decrypt a fixed size ciphertext
 
1283
        DecodingResult FixedLengthDecrypt(RandomNumberGenerator &rng, const byte *ciphertext, byte *plaintext, const NameValuePairs &parameters = g_nullNameValuePairs) const
 
1284
                {return Decrypt(rng, ciphertext, FixedCiphertextLength(), plaintext, parameters);}
 
1285
};
 
1286
 
 
1287
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
1288
typedef PK_CryptoSystem PK_FixedLengthCryptoSystem;
 
1289
typedef PK_Encryptor PK_FixedLengthEncryptor;
 
1290
typedef PK_Decryptor PK_FixedLengthDecryptor;
 
1291
#endif
 
1292
 
 
1293
//! interface for public-key signers and verifiers
 
1294
 
 
1295
/*! This class provides an interface common to signers and verifiers
 
1296
        for querying scheme properties.
 
1297
*/
 
1298
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_SignatureScheme
 
1299
{
 
1300
public:
 
1301
        //! invalid key exception, may be thrown by any function in this class if the private or public key has a length that can't be used
 
1302
        class CRYPTOPP_DLL InvalidKeyLength : public Exception
 
1303
        {
 
1304
        public:
 
1305
                InvalidKeyLength(const std::string &message) : Exception(OTHER_ERROR, message) {}
 
1306
        };
 
1307
 
 
1308
        //! key too short exception, may be thrown by any function in this class if the private or public key is too short to sign or verify anything
 
1309
        class CRYPTOPP_DLL KeyTooShort : public InvalidKeyLength
 
1310
        {
 
1311
        public:
 
1312
                KeyTooShort() : InvalidKeyLength("PK_Signer: key too short for this signature scheme") {}
 
1313
        };
 
1314
 
 
1315
        virtual ~PK_SignatureScheme() {}
 
1316
 
 
1317
        //! signature length if it only depends on the key, otherwise 0
 
1318
        virtual size_t SignatureLength() const =0;
 
1319
 
 
1320
        //! maximum signature length produced for a given length of recoverable message part
 
1321
        virtual size_t MaxSignatureLength(size_t recoverablePartLength = 0) const {return SignatureLength();}
 
1322
 
 
1323
        //! length of longest message that can be recovered, or 0 if this signature scheme does not support message recovery
 
1324
        virtual size_t MaxRecoverableLength() const =0;
 
1325
 
 
1326
        //! length of longest message that can be recovered from a signature of given length, or 0 if this signature scheme does not support message recovery
 
1327
        virtual size_t MaxRecoverableLengthFromSignatureLength(size_t signatureLength) const =0;
 
1328
 
 
1329
        //! requires a random number generator to sign
 
1330
        /*! if this returns false, NullRNG() can be passed to functions that take RandomNumberGenerator & */
 
1331
        virtual bool IsProbabilistic() const =0;
 
1332
 
 
1333
        //! whether or not a non-recoverable message part can be signed
 
1334
        virtual bool AllowNonrecoverablePart() const =0;
 
1335
 
 
1336
        //! if this function returns true, during verification you must input the signature before the message, otherwise you can input it at anytime */
 
1337
        virtual bool SignatureUpfront() const {return false;}
 
1338
 
 
1339
        //! whether you must input the recoverable part before the non-recoverable part during signing
 
1340
        virtual bool RecoverablePartFirst() const =0;
 
1341
};
 
1342
 
 
1343
//! interface for accumulating messages to be signed or verified
 
1344
/*! Only Update() should be called
 
1345
        on this class. No other functions inherited from HashTransformation should be called.
 
1346
*/
 
1347
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_MessageAccumulator : public HashTransformation
 
1348
{
 
1349
public:
 
1350
        //! should not be called on PK_MessageAccumulator
 
1351
        unsigned int DigestSize() const
 
1352
                {throw NotImplemented("PK_MessageAccumulator: DigestSize() should not be called");}
 
1353
        //! should not be called on PK_MessageAccumulator
 
1354
        void TruncatedFinal(byte *digest, size_t digestSize) 
 
1355
                {throw NotImplemented("PK_MessageAccumulator: TruncatedFinal() should not be called");}
 
1356
};
 
1357
 
 
1358
//! interface for public-key signers
 
1359
 
 
1360
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Signer : public PK_SignatureScheme, public PrivateKeyAlgorithm
 
1361
{
 
1362
public:
 
1363
        //! create a new HashTransformation to accumulate the message to be signed
 
1364
        virtual PK_MessageAccumulator * NewSignatureAccumulator(RandomNumberGenerator &rng) const =0;
 
1365
 
 
1366
        virtual void InputRecoverableMessage(PK_MessageAccumulator &messageAccumulator, const byte *recoverableMessage, size_t recoverableMessageLength) const =0;
 
1367
 
 
1368
        //! sign and delete messageAccumulator (even in case of exception thrown)
 
1369
        /*! \pre size of signature == MaxSignatureLength()
 
1370
                \return actual signature length
 
1371
        */
 
1372
        virtual size_t Sign(RandomNumberGenerator &rng, PK_MessageAccumulator *messageAccumulator, byte *signature) const;
 
1373
 
 
1374
        //! sign and restart messageAccumulator
 
1375
        /*! \pre size of signature == MaxSignatureLength()
 
1376
                \return actual signature length
 
1377
        */
 
1378
        virtual size_t SignAndRestart(RandomNumberGenerator &rng, PK_MessageAccumulator &messageAccumulator, byte *signature, bool restart=true) const =0;
 
1379
 
 
1380
        //! sign a message
 
1381
        /*! \pre size of signature == MaxSignatureLength()
 
1382
                \return actual signature length
 
1383
        */
 
1384
        virtual size_t SignMessage(RandomNumberGenerator &rng, const byte *message, size_t messageLen, byte *signature) const;
 
1385
 
 
1386
        //! sign a recoverable message
 
1387
        /*! \pre size of signature == MaxSignatureLength(recoverableMessageLength)
 
1388
                \return actual signature length
 
1389
        */
 
1390
        virtual size_t SignMessageWithRecovery(RandomNumberGenerator &rng, const byte *recoverableMessage, size_t recoverableMessageLength, 
 
1391
                const byte *nonrecoverableMessage, size_t nonrecoverableMessageLength, byte *signature) const;
 
1392
};
 
1393
 
 
1394
//! interface for public-key signature verifiers
 
1395
/*! The Recover* functions throw NotImplemented if the signature scheme does not support
 
1396
        message recovery.
 
1397
        The Verify* functions throw InvalidDataFormat if the scheme does support message
 
1398
        recovery and the signature contains a non-empty recoverable message part. The
 
1399
        Recovery* functions should be used in that case.
 
1400
*/
 
1401
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Verifier : public PK_SignatureScheme, public PublicKeyAlgorithm
 
1402
{
 
1403
public:
 
1404
        //! create a new HashTransformation to accumulate the message to be verified
 
1405
        virtual PK_MessageAccumulator * NewVerificationAccumulator() const =0;
 
1406
 
 
1407
        //! input signature into a message accumulator
 
1408
        virtual void InputSignature(PK_MessageAccumulator &messageAccumulator, const byte *signature, size_t signatureLength) const =0;
 
1409
 
 
1410
        //! check whether messageAccumulator contains a valid signature and message, and delete messageAccumulator (even in case of exception thrown)
 
1411
        virtual bool Verify(PK_MessageAccumulator *messageAccumulator) const;
 
1412
 
 
1413
        //! check whether messageAccumulator contains a valid signature and message, and restart messageAccumulator
 
1414
        virtual bool VerifyAndRestart(PK_MessageAccumulator &messageAccumulator) const =0;
 
1415
 
 
1416
        //! check whether input signature is a valid signature for input message
 
1417
        virtual bool VerifyMessage(const byte *message, size_t messageLen, 
 
1418
                const byte *signature, size_t signatureLength) const;
 
1419
 
 
1420
        //! recover a message from its signature
 
1421
        /*! \pre size of recoveredMessage == MaxRecoverableLengthFromSignatureLength(signatureLength)
 
1422
        */
 
1423
        virtual DecodingResult Recover(byte *recoveredMessage, PK_MessageAccumulator *messageAccumulator) const;
 
1424
 
 
1425
        //! recover a message from its signature
 
1426
        /*! \pre size of recoveredMessage == MaxRecoverableLengthFromSignatureLength(signatureLength)
 
1427
        */
 
1428
        virtual DecodingResult RecoverAndRestart(byte *recoveredMessage, PK_MessageAccumulator &messageAccumulator) const =0;
 
1429
 
 
1430
        //! recover a message from its signature
 
1431
        /*! \pre size of recoveredMessage == MaxRecoverableLengthFromSignatureLength(signatureLength)
 
1432
        */
 
1433
        virtual DecodingResult RecoverMessage(byte *recoveredMessage, 
 
1434
                const byte *nonrecoverableMessage, size_t nonrecoverableMessageLength, 
 
1435
                const byte *signature, size_t signatureLength) const;
 
1436
};
 
1437
 
 
1438
//! interface for domains of simple key agreement protocols
 
1439
 
 
1440
/*! A key agreement domain is a set of parameters that must be shared
 
1441
        by two parties in a key agreement protocol, along with the algorithms
 
1442
        for generating key pairs and deriving agreed values.
 
1443
*/
 
1444
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE SimpleKeyAgreementDomain : public KeyAgreementAlgorithm
 
1445
{
 
1446
public:
 
1447
        //! return length of agreed value produced
 
1448
        virtual unsigned int AgreedValueLength() const =0;
 
1449
        //! return length of private keys in this domain
 
1450
        virtual unsigned int PrivateKeyLength() const =0;
 
1451
        //! return length of public keys in this domain
 
1452
        virtual unsigned int PublicKeyLength() const =0;
 
1453
        //! generate private key
 
1454
        /*! \pre size of privateKey == PrivateKeyLength() */
 
1455
        virtual void GeneratePrivateKey(RandomNumberGenerator &rng, byte *privateKey) const =0;
 
1456
        //! generate public key
 
1457
        /*!     \pre size of publicKey == PublicKeyLength() */
 
1458
        virtual void GeneratePublicKey(RandomNumberGenerator &rng, const byte *privateKey, byte *publicKey) const =0;
 
1459
        //! generate private/public key pair
 
1460
        /*! \note equivalent to calling GeneratePrivateKey() and then GeneratePublicKey() */
 
1461
        virtual void GenerateKeyPair(RandomNumberGenerator &rng, byte *privateKey, byte *publicKey) const;
 
1462
        //! derive agreed value from your private key and couterparty's public key, return false in case of failure
 
1463
        /*! \note If you have previously validated the public key, use validateOtherPublicKey=false to save time.
 
1464
                \pre size of agreedValue == AgreedValueLength()
 
1465
                \pre length of privateKey == PrivateKeyLength()
 
1466
                \pre length of otherPublicKey == PublicKeyLength()
 
1467
        */
 
1468
        virtual bool Agree(byte *agreedValue, const byte *privateKey, const byte *otherPublicKey, bool validateOtherPublicKey=true) const =0;
 
1469
 
 
1470
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
1471
        bool ValidateDomainParameters(RandomNumberGenerator &rng) const
 
1472
                {return GetCryptoParameters().Validate(rng, 2);}
 
1473
#endif
 
1474
};
 
1475
 
 
1476
//! interface for domains of authenticated key agreement protocols
 
1477
 
 
1478
/*! In an authenticated key agreement protocol, each party has two
 
1479
        key pairs. The long-lived key pair is called the static key pair,
 
1480
        and the short-lived key pair is called the ephemeral key pair.
 
1481
*/
 
1482
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE AuthenticatedKeyAgreementDomain : public KeyAgreementAlgorithm
 
1483
{
 
1484
public:
 
1485
        //! return length of agreed value produced
 
1486
        virtual unsigned int AgreedValueLength() const =0;
 
1487
 
 
1488
        //! return length of static private keys in this domain
 
1489
        virtual unsigned int StaticPrivateKeyLength() const =0;
 
1490
        //! return length of static public keys in this domain
 
1491
        virtual unsigned int StaticPublicKeyLength() const =0;
 
1492
        //! generate static private key
 
1493
        /*! \pre size of privateKey == PrivateStaticKeyLength() */
 
1494
        virtual void GenerateStaticPrivateKey(RandomNumberGenerator &rng, byte *privateKey) const =0;
 
1495
        //! generate static public key
 
1496
        /*!     \pre size of publicKey == PublicStaticKeyLength() */
 
1497
        virtual void GenerateStaticPublicKey(RandomNumberGenerator &rng, const byte *privateKey, byte *publicKey) const =0;
 
1498
        //! generate private/public key pair
 
1499
        /*! \note equivalent to calling GenerateStaticPrivateKey() and then GenerateStaticPublicKey() */
 
1500
        virtual void GenerateStaticKeyPair(RandomNumberGenerator &rng, byte *privateKey, byte *publicKey) const;
 
1501
 
 
1502
        //! return length of ephemeral private keys in this domain
 
1503
        virtual unsigned int EphemeralPrivateKeyLength() const =0;
 
1504
        //! return length of ephemeral public keys in this domain
 
1505
        virtual unsigned int EphemeralPublicKeyLength() const =0;
 
1506
        //! generate ephemeral private key
 
1507
        /*! \pre size of privateKey == PrivateEphemeralKeyLength() */
 
1508
        virtual void GenerateEphemeralPrivateKey(RandomNumberGenerator &rng, byte *privateKey) const =0;
 
1509
        //! generate ephemeral public key
 
1510
        /*!     \pre size of publicKey == PublicEphemeralKeyLength() */
 
1511
        virtual void GenerateEphemeralPublicKey(RandomNumberGenerator &rng, const byte *privateKey, byte *publicKey) const =0;
 
1512
        //! generate private/public key pair
 
1513
        /*! \note equivalent to calling GenerateEphemeralPrivateKey() and then GenerateEphemeralPublicKey() */
 
1514
        virtual void GenerateEphemeralKeyPair(RandomNumberGenerator &rng, byte *privateKey, byte *publicKey) const;
 
1515
 
 
1516
        //! derive agreed value from your private keys and couterparty's public keys, return false in case of failure
 
1517
        /*! \note The ephemeral public key will always be validated.
 
1518
                      If you have previously validated the static public key, use validateStaticOtherPublicKey=false to save time.
 
1519
                \pre size of agreedValue == AgreedValueLength()
 
1520
                \pre length of staticPrivateKey == StaticPrivateKeyLength()
 
1521
                \pre length of ephemeralPrivateKey == EphemeralPrivateKeyLength()
 
1522
                \pre length of staticOtherPublicKey == StaticPublicKeyLength()
 
1523
                \pre length of ephemeralOtherPublicKey == EphemeralPublicKeyLength()
 
1524
        */
 
1525
        virtual bool Agree(byte *agreedValue,
 
1526
                const byte *staticPrivateKey, const byte *ephemeralPrivateKey,
 
1527
                const byte *staticOtherPublicKey, const byte *ephemeralOtherPublicKey,
 
1528
                bool validateStaticOtherPublicKey=true) const =0;
 
1529
 
 
1530
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
1531
        bool ValidateDomainParameters(RandomNumberGenerator &rng) const
 
1532
                {return GetCryptoParameters().Validate(rng, 2);}
 
1533
#endif
 
1534
};
 
1535
 
 
1536
// interface for password authenticated key agreement protocols, not implemented yet
 
1537
#if 0
 
1538
//! interface for protocol sessions
 
1539
/*! The methods should be called in the following order:
 
1540
 
 
1541
        InitializeSession(rng, parameters);     // or call initialize method in derived class
 
1542
        while (true)
 
1543
        {
 
1544
                if (OutgoingMessageAvailable())
 
1545
                {
 
1546
                        length = GetOutgoingMessageLength();
 
1547
                        GetOutgoingMessage(message);
 
1548
                        ; // send outgoing message
 
1549
                }
 
1550
 
 
1551
                if (LastMessageProcessed())
 
1552
                        break;
 
1553
 
 
1554
                ; // receive incoming message
 
1555
                ProcessIncomingMessage(message);
 
1556
        }
 
1557
        ; // call methods in derived class to obtain result of protocol session
 
1558
*/
 
1559
class ProtocolSession
 
1560
{
 
1561
public:
 
1562
        //! exception thrown when an invalid protocol message is processed
 
1563
        class ProtocolError : public Exception
 
1564
        {
 
1565
        public:
 
1566
                ProtocolError(ErrorType errorType, const std::string &s) : Exception(errorType, s) {}
 
1567
        };
 
1568
 
 
1569
        //! exception thrown when a function is called unexpectedly
 
1570
        /*! for example calling ProcessIncomingMessage() when ProcessedLastMessage() == true */
 
1571
        class UnexpectedMethodCall : public Exception
 
1572
        {
 
1573
        public:
 
1574
                UnexpectedMethodCall(const std::string &s) : Exception(OTHER_ERROR, s) {}
 
1575
        };
 
1576
 
 
1577
        ProtocolSession() : m_rng(NULL), m_throwOnProtocolError(true), m_validState(false) {}
 
1578
        virtual ~ProtocolSession() {}
 
1579
 
 
1580
        virtual void InitializeSession(RandomNumberGenerator &rng, const NameValuePairs &parameters) =0;
 
1581
 
 
1582
        bool GetThrowOnProtocolError() const {return m_throwOnProtocolError;}
 
1583
        void SetThrowOnProtocolError(bool throwOnProtocolError) {m_throwOnProtocolError = throwOnProtocolError;}
 
1584
 
 
1585
        bool HasValidState() const {return m_validState;}
 
1586
 
 
1587
        virtual bool OutgoingMessageAvailable() const =0;
 
1588
        virtual unsigned int GetOutgoingMessageLength() const =0;
 
1589
        virtual void GetOutgoingMessage(byte *message) =0;
 
1590
 
 
1591
        virtual bool LastMessageProcessed() const =0;
 
1592
        virtual void ProcessIncomingMessage(const byte *message, unsigned int messageLength) =0;
 
1593
 
 
1594
protected:
 
1595
        void HandleProtocolError(Exception::ErrorType errorType, const std::string &s) const;
 
1596
        void CheckAndHandleInvalidState() const;
 
1597
        void SetValidState(bool valid) {m_validState = valid;}
 
1598
 
 
1599
        RandomNumberGenerator *m_rng;
 
1600
 
 
1601
private:
 
1602
        bool m_throwOnProtocolError, m_validState;
 
1603
};
 
1604
 
 
1605
class KeyAgreementSession : public ProtocolSession
 
1606
{
 
1607
public:
 
1608
        virtual unsigned int GetAgreedValueLength() const =0;
 
1609
        virtual void GetAgreedValue(byte *agreedValue) const =0;
 
1610
};
 
1611
 
 
1612
class PasswordAuthenticatedKeyAgreementSession : public KeyAgreementSession
 
1613
{
 
1614
public:
 
1615
        void InitializePasswordAuthenticatedKeyAgreementSession(RandomNumberGenerator &rng, 
 
1616
                const byte *myId, unsigned int myIdLength, 
 
1617
                const byte *counterPartyId, unsigned int counterPartyIdLength, 
 
1618
                const byte *passwordOrVerifier, unsigned int passwordOrVerifierLength);
 
1619
};
 
1620
 
 
1621
class PasswordAuthenticatedKeyAgreementDomain : public KeyAgreementAlgorithm
 
1622
{
 
1623
public:
 
1624
        //! return whether the domain parameters stored in this object are valid
 
1625
        virtual bool ValidateDomainParameters(RandomNumberGenerator &rng) const
 
1626
                {return GetCryptoParameters().Validate(rng, 2);}
 
1627
 
 
1628
        virtual unsigned int GetPasswordVerifierLength(const byte *password, unsigned int passwordLength) const =0;
 
1629
        virtual void GeneratePasswordVerifier(RandomNumberGenerator &rng, const byte *userId, unsigned int userIdLength, const byte *password, unsigned int passwordLength, byte *verifier) const =0;
 
1630
 
 
1631
        enum RoleFlags {CLIENT=1, SERVER=2, INITIATOR=4, RESPONDER=8};
 
1632
 
 
1633
        virtual bool IsValidRole(unsigned int role) =0;
 
1634
        virtual PasswordAuthenticatedKeyAgreementSession * CreateProtocolSession(unsigned int role) const =0;
 
1635
};
 
1636
#endif
 
1637
 
 
1638
//! BER Decode Exception Class, may be thrown during an ASN1 BER decode operation
 
1639
class CRYPTOPP_DLL BERDecodeErr : public InvalidArgument
 
1640
{
 
1641
public: 
 
1642
        BERDecodeErr() : InvalidArgument("BER decode error") {}
 
1643
        BERDecodeErr(const std::string &s) : InvalidArgument(s) {}
 
1644
};
 
1645
 
 
1646
//! interface for encoding and decoding ASN1 objects
 
1647
class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE ASN1Object
 
1648
{
 
1649
public:
 
1650
        virtual ~ASN1Object() {}
 
1651
        //! decode this object from a BufferedTransformation, using BER (Basic Encoding Rules)
 
1652
        virtual void BERDecode(BufferedTransformation &bt) =0;
 
1653
        //! encode this object into a BufferedTransformation, using DER (Distinguished Encoding Rules)
 
1654
        virtual void DEREncode(BufferedTransformation &bt) const =0;
 
1655
        //! encode this object into a BufferedTransformation, using BER
 
1656
        /*! this may be useful if DEREncode() would be too inefficient */
 
1657
        virtual void BEREncode(BufferedTransformation &bt) const {DEREncode(bt);}
 
1658
};
 
1659
 
 
1660
#ifdef CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY
 
1661
typedef PK_SignatureScheme PK_SignatureSystem;
 
1662
typedef SimpleKeyAgreementDomain PK_SimpleKeyAgreementDomain;
 
1663
typedef AuthenticatedKeyAgreementDomain PK_AuthenticatedKeyAgreementDomain;
 
1664
#endif
 
1665
 
 
1666
NAMESPACE_END
 
1667
 
 
1668
#endif