patch #7319
[mldonkey.git] / src / utils / lib / CryptoPP.h
blob775a8989ce48262047c45aca6be2949e6440d231
1 ////////////////////////////////////////////////////////////////////////////////
2 //
3 // This file contains a subset of the Crypto++ library (version 5.2.1), with
4 // kind permission from Wei Dai. Please note that this file should not reflect
5 // on the real Crypto++ library in any way, as this file been greatly mangled to
6 // reduce the code-size, since this app only makes use of RSA classes (for Secure
7 // Identification) and the MD4 hashing class (for FileIDs).
8 //
9 // For the full Crypto++ library, please refer to the official Crypto++ website,
10 // which can be found at, http://www.cryptopp.com
11 //
12 ////////////////////////////////////////////////////////////////////////////////
13 //
14 // Compilation Copyright (c) 1995-2004 by Wei Dai. All rights reserved.
15 // This copyright applies only to this software distribution package
16 // as a compilation, and does not imply a copyright on any particular
17 // file in the package.
18 //
19 // The following files are copyrighted by their respective original authors,
20 // and their use is subject to additional licenses included in these files.
21 //
22 // mars.cpp - Copyright 1998 Brian Gladman.
24 // All other files in this compilation are placed in the public domain by
25 // Wei Dai and other contributors.
26 //
27 // I would like to thank the following authors for placing their works into
28 // the public domain:
29 //
30 // Joan Daemen - 3way.cpp
31 // Leonard Janke - cast.cpp, seal.cpp
32 // Steve Reid - cast.cpp
33 // Phil Karn - des.cpp
34 // Michael Paul Johnson - diamond.cpp
35 // Andrew M. Kuchling - md2.cpp, md4.cpp
36 // Colin Plumb - md5.cpp, md5mac.cpp
37 // Seal Woods - rc6.cpp
38 // Chris Morgan - rijndael.cpp
39 // Paulo Baretto - rijndael.cpp, skipjack.cpp, square.cpp
40 // Richard De Moliner - safer.cpp
41 // Matthew Skala - twofish.cpp
42 // Kevin Springle - camellia.cpp, shacal2.cpp, ttmac.cpp, whrlpool.cpp, ripemd.cpp
43 //
44 // Permission to use, copy, modify, and distribute this compilation for
45 // any purpose, including commercial applications, is hereby granted
46 // without fee, subject to the following restrictions:
47 //
48 // 1. Any copy or modification of this compilation in any form, except
49 // in object code form as part of an application software, must include
50 // the above copyright notice and this license.
51 //
52 // 2. Users of this software agree that any modification or extension
53 // they provide to Wei Dai will be considered public domain and not
54 // copyrighted unless it includes an explicit copyright notice.
55 //
56 // 3. Wei Dai makes no warranty or representation that the operation of the
57 // software in this compilation will be error-free, and Wei Dai is under no
58 // obligation to provide any services, by way of maintenance, update, or
59 // otherwise. THE SOFTWARE AND ANY DOCUMENTATION ARE PROVIDED "AS IS"
60 // WITHOUT EXPRESS OR IMPLIED WARRANTY INCLUDING, BUT NOT LIMITED TO,
61 // THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
62 // PURPOSE. IN NO EVENT WILL WEI DAI OR ANY OTHER CONTRIBUTOR BE LIABLE FOR
63 // DIRECT, INCIDENTAL OR CONSEQUENTIAL DAMAGES, EVEN IF
64 // ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
65 //
66 // 4. Users will not use Wei Dai or any other contributor's name in any
67 // publicity or advertising, without prior written consent in each case.
68 //
69 // 5. Export of this software from the United States may require a
70 // specific license from the United States Government. It is the
71 // responsibility of any person or organization contemplating export
72 // to obtain such a license before exporting.
73 //
74 // 6. Certain parts of this software may be protected by patents. It
75 // is the users' responsibility to obtain the appropriate
76 // licenses before using those parts.
77 //
78 // If this compilation is used in object code form in an application
79 // software, acknowledgement of the author is not required but would be
80 // appreciated. The contribution of any useful modifications or extensions
81 // to Wei Dai is not required but would also be appreciated.
82 //
83 ////////////////////////////////////////////////////////////////////////////////
85 #ifndef CRYPTOPP_H
86 #define CRYPTOPP_H
88 #include <inttypes.h>
89 #include <caml/config.h>
90 #include <stdio.h>
92 ////////////////////////////////////////////////////////////////////////////////
93 #ifndef CRYPTOPP_CONFIG_H5392
94 #define CRYPTOPP_CONFIG_H
96 // ***************** Important Settings ********************
98 // define this if running on a little-endian CPU
99 // big endian will be assumed if IS_LITTLE_ENDIAN is not defined
100 #ifndef ARCH_BIG_ENDIAN
101 # define IS_LITTLE_ENDIAN
102 #endif
104 // override #define in caml/compatibility.h
105 #undef flush
107 // define this if you want to disable all OS-dependent features,
108 // such as sockets and OS-provided random number generators
109 // #define NO_OS_DEPENDENCE
111 // Define this to use features provided by Microsoft's CryptoAPI.
112 // Currently the only feature used is random number generation.
113 // This macro will be ignored if NO_OS_DEPENDENCE is defined.
114 #define USE_MS_CRYPTOAPI
116 // Define this to 1 to enforce the requirement in FIPS 186-2 Change Notice 1 that only 1024 bit moduli be used
117 #ifndef DSA_1024_BIT_MODULUS_ONLY
118 # define DSA_1024_BIT_MODULUS_ONLY 1
119 #endif
121 // ***************** Less Important Settings ***************
123 #define GZIP_OS_CODE 0
125 // Try this if your CPU has 256K internal cache or a slow multiply instruction
126 // and you want a (possibly) faster IDEA implementation using log tables
127 // #define IDEA_LARGECACHE
129 // Define this if, for the linear congruential RNG, you want to use
130 // the original constants as specified in S.K. Park and K.W. Miller's
131 // CACM paper.
132 // #define LCRNG_ORIGINAL_NUMBERS
134 // choose which style of sockets to wrap (mostly useful for cygwin which has both)
135 #define PREFER_BERKELEY_STYLE_SOCKETS
136 // #define PREFER_WINDOWS_STYLE_SOCKETS
138 // ***************** Important Settings Again ********************
139 // But the defaults should be ok.
141 // namespace support is now required
142 #ifdef NO_NAMESPACE
143 # error namespace support is now required
144 #endif
146 // Define this to workaround a Microsoft CryptoAPI bug where
147 // each call to CryptAcquireContext causes a 100 KB memory leak.
148 // Defining this will cause Crypto++ to make only one call to CryptAcquireContext.
149 #define WORKAROUND_MS_BUG_Q258000
151 #ifdef CRYPTOPP_DOXYGEN_PROCESSING
152 // Avoid putting "CryptoPP::" in front of everything in Doxygen output
153 # define CryptoPP
154 # define NAMESPACE_BEGIN(x)
155 # define NAMESPACE_END
156 // Get Doxygen to generate better documentation for these typedefs
157 # define DOCUMENTED_TYPEDEF(x, y) class y : public x {};
158 #else
159 # define NAMESPACE_BEGIN(x) namespace x {
160 # define NAMESPACE_END }
161 # define DOCUMENTED_TYPEDEF(x, y) typedef x y;
162 #endif
163 #define ANONYMOUS_NAMESPACE_BEGIN namespace {
164 #define USING_NAMESPACE(x) using namespace x;
165 #define DOCUMENTED_NAMESPACE_BEGIN(x) namespace x {
166 #define DOCUMENTED_NAMESPACE_END }
168 // What is the type of the third parameter to bind?
169 // For Unix, the new standard is ::socklen_t (typically unsigned int), and the old standard is int.
170 // Unfortunately there is no way to tell whether or not socklen_t is defined.
171 // To work around this, TYPE_OF_SOCKLEN_T is a macro so that you can change it from the makefile.
172 #ifndef TYPE_OF_SOCKLEN_T
173 # if defined(_WIN32) || defined(__CYGWIN__) || defined(__MACH__)
174 # define TYPE_OF_SOCKLEN_T int
175 # else
176 # define TYPE_OF_SOCKLEN_T ::socklen_t
177 # endif
178 #endif
180 #if defined(__CYGWIN__) && defined(PREFER_WINDOWS_STYLE_SOCKETS)
181 # define __USE_W32_SOCKETS
182 #endif
184 typedef unsigned char byte; // put in global namespace to avoid ambiguity with other byte typedefs
186 NAMESPACE_BEGIN(CryptoPP)
188 typedef unsigned short word16;
189 typedef unsigned int word32;
191 #if defined(__GNUC__) || defined(__MWERKS__)
192 #define WORD64_AVAILABLE
193 typedef uint64_t word64;
194 #define W64LIT(x) x##LL
195 #elif defined(_MSC_VER) || defined(__BCPLUSPLUS__)
196 #define WORD64_AVAILABLE
197 typedef unsigned __int64 word64;
198 #define W64LIT(x) x##ui64
199 #endif
201 // define largest word type
202 #ifdef WORD64_AVAILABLE
203 typedef word64 lword;
204 #else
205 typedef word32 lword;
206 #endif
208 #if defined(__alpha__) || defined(__ia64__) || defined(_ARCH_PPC64) || defined(__x86_64__) || defined(__mips64)
209 // These platforms have 64-bit CPU registers. Unfortunately most C++ compilers doesn't
210 // allow any way to access the 64-bit by 64-bit multiply instruction without using
211 // assembly, so in order to use word64 as word, the assembly instruction must be defined
212 // in Dword::Multiply().
213 typedef word32 hword;
214 typedef word64 word;
215 #else
216 #define CRYPTOPP_NATIVE_DWORD_AVAILABLE
217 #ifdef WORD64_AVAILABLE
218 #define CRYPTOPP_SLOW_WORD64 // defined this if your CPU is not 64-bit to use alternative code that avoids word64
219 typedef word16 hword;
220 typedef word32 word;
221 typedef word64 dword;
222 #else
223 typedef word8 hword;
224 typedef word16 word;
225 typedef word32 dword;
226 #endif
227 #endif
229 const unsigned int WORD_SIZE = sizeof(word);
230 const unsigned int WORD_BITS = WORD_SIZE * 8;
232 #if defined(_MSC_VER) || defined(__BCPLUSPLUS__)
233 #define INTEL_INTRINSICS
234 #define FAST_ROTATE
235 #elif defined(__MWERKS__) && TARGET_CPU_PPC
236 #define PPC_INTRINSICS
237 #define FAST_ROTATE
238 #elif defined(__GNUC__) && defined(__i386__)
239 // GCC does peephole optimizations which should result in using rotate instructions
240 #define FAST_ROTATE
241 #endif
243 NAMESPACE_END
245 // VC60 workaround: it doesn't allow typename in some places
246 #if defined(_MSC_VER) && (_MSC_VER < 1300)
247 #define CPP_TYPENAME
248 #else
249 #define CPP_TYPENAME typename
250 #endif
252 #define CRYPTOPP_NO_VTABLE
254 #ifdef _MSC_VER
255 // 4231: nonstandard extension used : 'extern' before template explicit instantiation
256 // 4250: dominance
257 // 4251: member needs to have dll-interface
258 // 4275: base needs to have dll-interface
259 // 4660: explicitly instantiating a class that's already implicitly instantiated
260 // 4661: no suitable definition provided for explicit template instantiation request
261 // 4786: identifer was truncated in debug information
262 // 4355: 'this' : used in base member initializer list
263 # pragma warning(disable: 4231 4250 4251 4275 4660 4661 4786 4355)
264 #endif
266 #if (defined(_MSC_VER) && _MSC_VER <= 1300) || defined(__MWERKS__) || defined(_STLPORT_VERSION)
267 #define CRYPTOPP_DISABLE_UNCAUGHT_EXCEPTION
268 #endif
270 #ifndef CRYPTOPP_DISABLE_UNCAUGHT_EXCEPTION
271 #define CRYPTOPP_UNCAUGHT_EXCEPTION_AVAILABLE
272 #endif
274 // CodeWarrior defines _MSC_VER
275 #if !defined(CRYPTOPP_DISABLE_X86ASM) && ((defined(_MSC_VER) && !defined(__MWERKS__) && defined(_M_IX86)) || (defined(__GNUC__) && defined(__i386__)))
276 // The x86 version of MacOSX fails when asm is enabled.
277 #if !defined(__i386__) || !defined(__APPLE__)
278 #define CRYPTOPP_X86ASM_AVAILABLE
279 #endif
280 #endif
282 // ***************** determine availability of OS features ********************
284 #ifndef NO_OS_DEPENDENCE
286 #if defined(_WIN32) || defined(__CYGWIN__)
287 #define CRYPTOPP_WIN32_AVAILABLE
288 #endif
290 #if defined(__unix__) || defined(__MACH__) || defined(__NetBSD__) || defined(__BEOS__) || defined(__MORPHOS__)
291 #define CRYPTOPP_UNIX_AVAILABLE
292 #endif
294 #if defined(WORD64_AVAILABLE) && (defined(CRYPTOPP_WIN32_AVAILABLE) || defined(CRYPTOPP_UNIX_AVAILABLE))
295 # define HIGHRES_TIMER_AVAILABLE
296 #endif
298 #ifdef CRYPTOPP_UNIX_AVAILABLE
299 # define HAS_BERKELEY_STYLE_SOCKETS
300 #endif
302 #ifdef CRYPTOPP_WIN32_AVAILABLE
303 # define HAS_WINDOWS_STYLE_SOCKETS
304 #endif
306 #if defined(HIGHRES_TIMER_AVAILABLE) && (defined(HAS_BERKELEY_STYLE_SOCKETS) || defined(HAS_WINDOWS_STYLE_SOCKETS))
307 # define SOCKETS_AVAILABLE
308 #endif
310 #if defined(HAS_WINDOWS_STYLE_SOCKETS) && (!defined(HAS_BERKELEY_STYLE_SOCKETS) || defined(PREFER_WINDOWS_STYLE_SOCKETS))
311 # define USE_WINDOWS_STYLE_SOCKETS
312 #else
313 # define USE_BERKELEY_STYLE_SOCKETS
314 #endif
316 #if defined(CRYPTOPP_WIN32_AVAILABLE) && !defined(USE_BERKELEY_STYLE_SOCKETS)
317 # define WINDOWS_PIPES_AVAILABLE
318 #endif
320 #if defined(CRYPTOPP_WIN32_AVAILABLE) && defined(USE_MS_CRYPTOAPI)
321 # define NONBLOCKING_RNG_AVAILABLE
322 # define OS_RNG_AVAILABLE
323 #endif
325 #if defined(CRYPTOPP_UNIX_AVAILABLE) || defined(CRYPTOPP_DOXYGEN_PROCESSING)
326 # define NONBLOCKING_RNG_AVAILABLE
327 # define BLOCKING_RNG_AVAILABLE
328 # define OS_RNG_AVAILABLE
329 # define HAS_PTHREADS
330 # define THREADS_AVAILABLE
331 #endif
333 #ifdef CRYPTOPP_WIN32_AVAILABLE
334 # define HAS_WINTHREADS
335 # define THREADS_AVAILABLE
336 #endif
338 #if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__)
339 # define CRYPTOPP_MALLOC_ALIGNMENT_IS_16
340 #endif
342 #if defined(__linux__) || defined(__sun__) || defined(__CYGWIN__)
343 # define CRYPTOPP_MEMALIGN_AVAILABLE
344 #endif
346 #endif // NO_OS_DEPENDENCE
348 // ***************** DLL related ********************
350 #define CRYPTOPP_DLL
351 #define CRYPTOPP_API
352 #define CRYPTOPP_CDECL
354 #if defined(CRYPTOPP_MANUALLY_INSTANTIATE_TEMPLATES) && !defined(CRYPTOPP_EXPORTS)
355 #define CRYPTOPP_STATIC_TEMPLATE_CLASS template class
356 #elif defined(__MWERKS__)
357 #define CRYPTOPP_STATIC_TEMPLATE_CLASS extern class
358 #else
359 #define CRYPTOPP_STATIC_TEMPLATE_CLASS extern template class
360 #endif
362 #endif
363 ////////////////////////////////////////////////////////////////////////////////
367 ////////////////////////////////////////////////////////////////////////////////
368 #ifndef CRYPTOPP_STDCPP_H
369 #define CRYPTOPP_STDCPP_H
371 #include <stddef.h>
372 #include <assert.h>
373 #include <limits.h>
374 #include <memory>
375 #include <string>
376 #include <exception>
377 #include <typeinfo>
378 #include <string.h>
381 #ifdef _MSC_VER
382 #include <algorithm>
383 #include <map>
384 #include <vector>
385 #include <locale>
387 // re-disable this
388 #pragma warning(disable: 4231)
389 #endif
391 #if defined(_MSC_VER) && defined(_CRTAPI1)
392 #define CRYPTOPP_MSVCRT6
393 #endif
395 #endif
396 ////////////////////////////////////////////////////////////////////////////////
400 ////////////////////////////////////////////////////////////////////////////////
401 // cryptlib.h - written and placed in the public domain by Wei Dai
402 /*! \file
403 This file contains the declarations for the abstract base
404 classes that provide a uniform interface to this library.
407 /*! \mainpage <a href="http://www.cryptopp.com">Crypto++</a><sup><small>TM</small></sup> Library 5.2.1 Reference Manual
408 <dl>
409 <dt>Abstract Base Classes<dd>
410 cryptlib.h
411 <dt>Symmetric Ciphers<dd>
412 SymmetricCipherDocumentation
413 <dt>Hash Functions<dd>
414 HAVAL, MD2, MD4, MD5, PanamaHash, RIPEMD160, RIPEMD320, RIPEMD128, RIPEMD256, SHA, SHA256, SHA384, SHA512, Tiger, Whirlpool
415 <dt>Non-Cryptographic Checksums<dd>
416 CRC32, Adler32
417 <dt>Message Authentication Codes<dd>
418 #MD5MAC, XMACC, HMAC, CBC_MAC, DMAC, PanamaMAC, TTMAC
419 <dt>Random Number Generators<dd>
420 NullRNG(), LC_RNG, RandomPool, BlockingRng, NonblockingRng, AutoSeededRandomPool, AutoSeededX917RNG
421 <dt>Password-based Cryptography<dd>
422 PasswordBasedKeyDerivationFunction
423 <dt>Public Key Cryptosystems<dd>
424 DLIES, ECIES, LUCES, RSAES, RabinES, LUC_IES
425 <dt>Public Key Signature Schemes<dd>
426 DSA, GDSA, ECDSA, NR, ECNR, LUCSS, RSASS, RabinSS, RWSS, ESIGN
427 <dt>Key Agreement<dd>
428 #DH, DH2, #MQV, ECDH, ECMQV, XTR_DH
429 <dt>Algebraic Structures<dd>
430 Integer, PolynomialMod2, PolynomialOver, RingOfPolynomialsOver,
431 ModularArithmetic, MontgomeryRepresentation, GFP2_ONB,
432 GF2NP, GF256, GF2_32, EC2N, ECP
433 <dt>Secret Sharing and Information Dispersal<dd>
434 SecretSharing, SecretRecovery, InformationDispersal, InformationRecovery
435 <dt>Compression<dd>
436 Deflator, Inflator, Gzip, Gunzip, ZlibCompressor, ZlibDecompressor
437 <dt>Input Source Classes<dd>
438 StringSource, FileSource, SocketSource, WindowsPipeSource, RandomNumberSource
439 <dt>Output Sink Classes<dd>
440 StringSinkTemplate, ArraySink, FileSink, SocketSink, WindowsPipeSink
441 <dt>Filter Wrappers<dd>
442 StreamTransformationFilter, HashFilter, HashVerificationFilter, SignerFilter, SignatureVerificationFilter
443 <dt>Binary to Text Encoders and Decoders<dd>
444 HexEncoder, HexDecoder, Base64Encoder, Base64Decoder, Base32Encoder, Base32Decoder
445 <dt>Wrappers for OS features<dd>
446 Timer, Socket, WindowsHandle, ThreadLocalStorage, ThreadUserTimer
447 <dt>FIPS 140 related<dd>
448 fips140.h
449 </dl>
451 In the FIPS 140-2 validated DLL version of Crypto++, only the following implementation class are available.
452 <dl>
453 <dt>Block Ciphers<dd>
454 AES, DES_EDE2, DES_EDE3, SKIPJACK
455 <dt>Cipher Modes (replace template parameter BC with one of the block ciphers above)<dd>
456 ECB_Mode\<BC\>, CTR_Mode\<BC\>, CBC_Mode\<BC\>, CFB_Mode\<BC\>, OFB_Mode\<BC\>
457 <dt>Hash Functions<dd>
459 <dt>Public Key Signature Schemes<dd>
460 RSASS\<PKCS1v15, SHA\>, DSA, ECDSA\<ECP, SHA\>, ECDSA\<EC2N, SHA\>
461 <dt>Message Authentication Codes<dd>
462 HMAC\<SHA\>, CBC_MAC\<DES_EDE2\>, CBC_MAC\<DES_EDE3\>
463 <dt>Random Number Generators<dd>
464 AutoSeededX917RNG\<DES_EDE3\>
465 <dt>Key Agreement<dd>
467 <dt>Public Key Cryptosystems<dd>
468 RSAES\<OAEP\<SHA\> \>
469 </dl>
471 <p>This reference manual is a work in progress. Some classes are still lacking detailed descriptions.
472 <p>Click <a href="CryptoPPRef.zip">here</a> to download a zip archive containing this manual.
473 <p>Thanks to Ryan Phillips for providing the Doxygen configuration file
474 and getting me started with this manual.
477 #ifndef CRYPTOPP_CRYPTLIB_H
478 #define CRYPTOPP_CRYPTLIB_H
480 //- #include "config.h"
481 //- #include "stdcpp.h"
483 NAMESPACE_BEGIN(CryptoPP)
485 // forward declarations
486 class Integer;
488 //! used to specify a direction for a cipher to operate in (encrypt or decrypt)
489 enum CipherDir {ENCRYPTION, DECRYPTION};
491 // VC60 workaround: using enums as template parameters causes problems
492 template <typename ENUM_TYPE, int VALUE>
493 struct EnumToType
495 static ENUM_TYPE ToEnum() {return (ENUM_TYPE)VALUE;}
498 enum ByteOrder {LITTLE_ENDIAN_ORDER = 0, BIG_ENDIAN_ORDER = 1};
499 typedef EnumToType<ByteOrder, LITTLE_ENDIAN_ORDER> LittleEndian;
500 typedef EnumToType<ByteOrder, BIG_ENDIAN_ORDER> BigEndian;
502 //! base class for all exceptions thrown by Crypto++
503 class CRYPTOPP_DLL Exception : public std::exception
505 public:
506 //! error types
507 enum ErrorType {
508 //! a method is not implemented
509 NOT_IMPLEMENTED,
510 //! invalid function argument
511 INVALID_ARGUMENT,
512 //! BufferedTransformation received a Flush(true) signal but can't flush buffers
513 CANNOT_FLUSH,
514 //! data integerity check (such as CRC or MAC) failed
515 DATA_INTEGRITY_CHECK_FAILED,
516 //! received input data that doesn't conform to expected format
517 INVALID_DATA_FORMAT,
518 //! error reading from input device or writing to output device
519 IO_ERROR,
520 //! some error not belong to any of the above categories
521 OTHER_ERROR
524 explicit Exception(ErrorType errorType, const std::string &s) : m_errorType(errorType), m_what(s) {}
525 virtual ~Exception() throw() {}
526 const char *what() const throw() {return (m_what.c_str());}
527 const std::string &GetWhat() const {return m_what;}
528 void SetWhat(const std::string &s) {m_what = s;}
529 ErrorType GetErrorType() const {return m_errorType;}
530 void SetErrorType(ErrorType errorType) {m_errorType = errorType;}
532 private:
533 ErrorType m_errorType;
534 std::string m_what;
537 //! exception thrown when an invalid argument is detected
538 class CRYPTOPP_DLL InvalidArgument : public Exception
540 public:
541 explicit InvalidArgument(const std::string &s) : Exception(INVALID_ARGUMENT, s) {}
544 //! exception thrown by decryption filters when trying to decrypt an invalid ciphertext
545 class CRYPTOPP_DLL InvalidDataFormat : public Exception
547 public:
548 explicit InvalidDataFormat(const std::string &s) : Exception(INVALID_DATA_FORMAT, s) {}
551 //! exception thrown by a class if a non-implemented method is called
552 class CRYPTOPP_DLL NotImplemented : public Exception
554 public:
555 explicit NotImplemented(const std::string &s) : Exception(NOT_IMPLEMENTED, s) {}
558 //! exception thrown by a class when Flush(true) is called but it can't completely flush its buffers
559 class CRYPTOPP_DLL CannotFlush : public Exception
561 public:
562 explicit CannotFlush(const std::string &s) : Exception(CANNOT_FLUSH, s) {}
565 //! error reported by the operating system
566 class CRYPTOPP_DLL OS_Error : public Exception
568 public:
569 OS_Error(ErrorType errorType, const std::string &s, const std::string& operation, int errorCode)
570 : Exception(errorType, s), m_operation(operation), m_errorCode(errorCode) {}
571 ~OS_Error() throw() {}
573 // the operating system API that reported the error
574 const std::string & GetOperation() const {return m_operation;}
575 // the error code return by the operating system
576 int GetErrorCode() const {return m_errorCode;}
578 protected:
579 std::string m_operation;
580 int m_errorCode;
583 //! used to return decoding results
584 struct CRYPTOPP_DLL DecodingResult
586 explicit DecodingResult() : isValidCoding(false), messageLength(0) {}
587 explicit DecodingResult(unsigned int len) : isValidCoding(true), messageLength(len) {}
589 bool operator==(const DecodingResult &rhs) const {return isValidCoding == rhs.isValidCoding && messageLength == rhs.messageLength;}
590 bool operator!=(const DecodingResult &rhs) const {return !operator==(rhs);}
592 bool isValidCoding;
593 unsigned int messageLength;
597 //! interface for retrieving values given their names
598 /*! \note This class is used to safely pass a variable number of arbitrarily typed arguments to functions
599 and to read values from keys and crypto parameters.
600 \note To obtain an object that implements NameValuePairs for the purpose of parameter
601 passing, use the MakeParameters() function.
602 \note To get a value from NameValuePairs, you need to know the name and the type of the value.
603 Call GetValueNames() on a NameValuePairs object to obtain a list of value names that it supports.
604 Then look at the Name namespace documentation to see what the type of each value is, or
605 alternatively, call GetIntValue() with the value name, and if the type is not int, a
606 ValueTypeMismatch exception will be thrown and you can get the actual type from the exception object.
608 class CRYPTOPP_NO_VTABLE NameValuePairs
610 public:
611 virtual ~NameValuePairs() {}
613 //! exception thrown when trying to retrieve a value using a different type than expected
614 class CRYPTOPP_DLL ValueTypeMismatch : public InvalidArgument
616 public:
617 ValueTypeMismatch(const std::string &name, const std::type_info &stored, const std::type_info &retrieving)
618 : InvalidArgument("NameValuePairs: type mismatch for '" + name + "', stored '" + stored.name() + "', trying to retrieve '" + retrieving.name() + "'")
619 , m_stored(stored), m_retrieving(retrieving) {}
621 const std::type_info & GetStoredTypeInfo() const {return m_stored;}
622 const std::type_info & GetRetrievingTypeInfo() const {return m_retrieving;}
624 private:
625 const std::type_info &m_stored;
626 const std::type_info &m_retrieving;
629 //! get a copy of this object or a subobject of it
630 template <class T>
631 bool GetThisObject(T &object) const
633 return GetValue((std::string("ThisObject:")+typeid(T).name()).c_str(), object);
636 //! get a pointer to this object, as a pointer to T
637 template <class T>
638 bool GetThisPointer(T *&p) const
640 return GetValue((std::string("ThisPointer:")+typeid(T).name()).c_str(), p);
643 //! get a named value, returns true if the name exists
644 template <class T>
645 bool GetValue(const char *name, T &value) const
647 return GetVoidValue(name, typeid(T), &value);
650 //! get a named value, returns the default if the name doesn't exist
651 template <class T>
652 T GetValueWithDefault(const char *name, T defaultValue) const
654 GetValue(name, defaultValue);
655 return defaultValue;
658 //! get a list of value names that can be retrieved
659 CRYPTOPP_DLL std::string GetValueNames() const
660 {std::string result; GetValue("ValueNames", result); return result;}
662 //! get a named value with type int
663 /*! used to ensure we don't accidentally try to get an unsigned int
664 or some other type when we mean int (which is the most common case) */
665 CRYPTOPP_DLL bool GetIntValue(const char *name, int &value) const
666 {return GetValue(name, value);}
668 //! get a named value with type int, with default
669 CRYPTOPP_DLL int GetIntValueWithDefault(const char *name, int defaultValue) const
670 {return GetValueWithDefault(name, defaultValue);}
672 //! used by derived classes to check for type mismatch
673 CRYPTOPP_DLL static void ThrowIfTypeMismatch(const char *name, const std::type_info &stored, const std::type_info &retrieving)
674 {if (stored != retrieving) throw ValueTypeMismatch(name, stored, retrieving);}
676 template <class T>
677 void GetRequiredParameter(const char *className, const char *name, T &value) const
679 if (!GetValue(name, value))
680 throw InvalidArgument(std::string(className) + ": missing required parameter '" + name + "'");
683 CRYPTOPP_DLL void GetRequiredIntParameter(const char *className, const char *name, int &value) const
685 if (!GetIntValue(name, value))
686 throw InvalidArgument(std::string(className) + ": missing required parameter '" + name + "'");
689 //! to be implemented by derived classes, users should use one of the above functions instead
690 CRYPTOPP_DLL virtual bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const =0;
693 //! empty set of name-value pairs
694 class CRYPTOPP_DLL NullNameValuePairs : public NameValuePairs
696 public:
697 bool GetVoidValue(const char* /* name */, const std::type_info& /* valueType */, void* /* pValue */) const {return false;}
700 //! _
701 extern CRYPTOPP_DLL const NullNameValuePairs g_nullNameValuePairs;
703 // ********************************************************
705 //! interface for cloning objects, this is not implemented by most classes yet
706 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Clonable
708 public:
709 virtual ~Clonable() {}
710 //! this is not implemented by most classes yet
711 virtual Clonable* Clone() const {throw NotImplemented("Clone() is not implemented yet.");} // TODO: make this =0
714 //! interface for all crypto algorithms
716 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Algorithm : public Clonable
718 public:
719 /*! When FIPS 140-2 compliance is enabled and checkSelfTestStatus == true,
720 this constructor throws SelfTestFailure if the self test hasn't been run or fails. */
721 Algorithm(bool checkSelfTestStatus = true);
722 //! returns name of this algorithm, not universally implemented yet
723 virtual std::string AlgorithmName() const {return "unknown";}
726 //! keying interface for crypto algorithms that take byte strings as keys
728 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE SimpleKeyingInterface
730 public:
731 virtual ~SimpleKeyingInterface() {};
733 //! returns smallest valid key length in bytes */
734 virtual unsigned int MinKeyLength() const =0;
735 //! returns largest valid key length in bytes */
736 virtual unsigned int MaxKeyLength() const =0;
737 //! returns default (recommended) key length in bytes */
738 virtual unsigned int DefaultKeyLength() const =0;
740 //! returns the smallest valid key length in bytes that is >= min(n, GetMaxKeyLength())
741 virtual unsigned int GetValidKeyLength(unsigned int n) const =0;
743 //! returns whether n is a valid key length
744 virtual bool IsValidKeyLength(unsigned int n) const
745 {return n == GetValidKeyLength(n);}
747 //! set or reset the key of this object
748 /*! \param params is used to specify Rounds, BlockSize, etc */
749 virtual void SetKey(const byte *key, unsigned int length, const NameValuePairs &params = g_nullNameValuePairs) =0;
751 //! calls SetKey() with an NameValuePairs object that just specifies "Rounds"
752 void SetKeyWithRounds(const byte *key, unsigned int length, int rounds);
754 //! calls SetKey() with an NameValuePairs object that just specifies "IV"
755 void SetKeyWithIV(const byte *key, unsigned int length, const byte *iv);
757 enum IV_Requirement {STRUCTURED_IV = 0, RANDOM_IV, UNPREDICTABLE_RANDOM_IV, INTERNALLY_GENERATED_IV, NOT_RESYNCHRONIZABLE};
758 //! returns the minimal requirement for secure IVs
759 virtual IV_Requirement IVRequirement() const =0;
761 //! returns whether this object can be resynchronized (i.e. supports initialization vectors)
762 /*! If this function returns true, and no IV is passed to SetKey() and CanUseStructuredIVs()==true, an IV of all 0's will be assumed. */
763 bool IsResynchronizable() const {return IVRequirement() < NOT_RESYNCHRONIZABLE;}
764 //! returns whether this object can use random IVs (in addition to ones returned by GetNextIV)
765 bool CanUseRandomIVs() const {return IVRequirement() <= UNPREDICTABLE_RANDOM_IV;}
766 //! returns whether this object can use random but possibly predictable IVs (in addition to ones returned by GetNextIV)
767 bool CanUsePredictableIVs() const {return IVRequirement() <= RANDOM_IV;}
768 //! returns whether this object can use structured IVs, for example a counter (in addition to ones returned by GetNextIV)
769 bool CanUseStructuredIVs() const {return IVRequirement() <= STRUCTURED_IV;}
771 //! returns size of IVs used by this object
772 virtual unsigned int IVSize() const {throw NotImplemented("SimpleKeyingInterface: this object doesn't support resynchronization");}
773 //! resynchronize with an IV
774 virtual void Resynchronize(const byte* /* IV */) {throw NotImplemented("SimpleKeyingInterface: this object doesn't support resynchronization");}
775 //! get a secure IV for the next message
776 /*! This method should be called after you finish encrypting one message and are ready to start the next one.
777 After calling it, you must call SetKey() or Resynchronize() before using this object again.
778 This method is not implemented on decryption objects. */
779 virtual void GetNextIV(byte* /* IV */) {throw NotImplemented("SimpleKeyingInterface: this object doesn't support GetNextIV()");}
781 protected:
782 void ThrowIfInvalidKeyLength(const Algorithm &algorithm, unsigned int length);
783 void ThrowIfResynchronizable(); // to be called when no IV is passed
784 void ThrowIfInvalidIV(const byte *iv); // check for NULL IV if it can't be used
785 const byte * GetIVAndThrowIfInvalid(const NameValuePairs &params);
787 inline void AssertValidKeyLength(unsigned int length) const
789 assert(IsValidKeyLength(length));
793 //! interface for the data processing part of block ciphers
795 /*! Classes derived from BlockTransformation are block ciphers
796 in ECB mode (for example the DES::Encryption class), which are stateless,
797 and they can make assumptions about the memory alignment of their inputs and outputs.
798 These classes should not be used directly, but only in combination with
799 a mode class (see CipherModeDocumentation in modes.h).
801 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE BlockTransformation : public Algorithm
803 public:
804 //! encrypt or decrypt inBlock, xor with xorBlock, and write to outBlock
805 virtual void ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const =0;
807 //! encrypt or decrypt one block
808 /*! \pre size of inBlock and outBlock == BlockSize() */
809 void ProcessBlock(const byte *inBlock, byte *outBlock) const
810 {ProcessAndXorBlock(inBlock, NULL, outBlock);}
812 //! encrypt or decrypt one block in place
813 void ProcessBlock(byte *inoutBlock) const
814 {ProcessAndXorBlock(inoutBlock, NULL, inoutBlock);}
816 //! block size of the cipher in bytes
817 virtual unsigned int BlockSize() const =0;
819 //! block pointers must be divisible by this
820 virtual unsigned int BlockAlignment() const {return 4;}
822 //! returns true if this is a permutation (i.e. there is an inverse transformation)
823 virtual bool IsPermutation() const {return true;}
825 //! returns true if this is an encryption object
826 virtual bool IsForwardTransformation() const =0;
828 //! return number of blocks that can be processed in parallel, for bit-slicing implementations
829 virtual unsigned int OptimalNumberOfParallelBlocks() const {return 1;}
831 //! encrypt or decrypt multiple blocks, for bit-slicing implementations
832 virtual void ProcessAndXorMultipleBlocks(const byte *inBlocks, const byte *xorBlocks, byte *outBlocks, unsigned int numberOfBlocks) const;
835 //! interface for the data processing part of stream ciphers
837 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE StreamTransformation : public Algorithm
839 public:
840 //! return a reference to this object,
841 /*! This function is useful for passing a temporary StreamTransformation object to a
842 function that takes a non-const reference. */
843 StreamTransformation& Ref() {return *this;}
845 //! returns block size, if input must be processed in blocks, otherwise 1
846 virtual unsigned int MandatoryBlockSize() const {return 1;}
848 //! returns the input block size that is most efficient for this cipher
849 /*! \note optimal input length is n * OptimalBlockSize() - GetOptimalBlockSizeUsed() for any n > 0 */
850 virtual unsigned int OptimalBlockSize() const {return MandatoryBlockSize();}
851 //! returns how much of the current block is used up
852 virtual unsigned int GetOptimalBlockSizeUsed() const {return 0;}
854 //! returns how input should be aligned for optimal performance
855 virtual unsigned int OptimalDataAlignment() const {return 1;}
857 //! encrypt or decrypt an array of bytes of specified length
858 /*! \note either inString == outString, or they don't overlap */
859 virtual void ProcessData(byte *outString, const byte *inString, unsigned int length) =0;
861 //! for ciphers where the last block of data is special, encrypt or decrypt the last block of data
862 /*! For now the only use of this function is for CBC-CTS mode. */
863 virtual void ProcessLastBlock(byte *outString, const byte *inString, unsigned int length);
864 //! returns the minimum size of the last block, 0 indicating the last block is not special
865 virtual unsigned int MinLastBlockSize() const {return 0;}
867 //! same as ProcessData(inoutString, inoutString, length)
868 inline void ProcessString(byte *inoutString, unsigned int length)
869 {ProcessData(inoutString, inoutString, length);}
870 //! same as ProcessData(outString, inString, length)
871 inline void ProcessString(byte *outString, const byte *inString, unsigned int length)
872 {ProcessData(outString, inString, length);}
873 //! implemented as {ProcessData(&input, &input, 1); return input;}
874 inline byte ProcessByte(byte input)
875 {ProcessData(&input, &input, 1); return input;}
877 //! returns whether this cipher supports random access
878 virtual bool IsRandomAccess() const =0;
879 //! for random access ciphers, seek to an absolute position
880 virtual void Seek(lword /* n */)
882 assert(!IsRandomAccess());
883 throw NotImplemented("StreamTransformation: this object doesn't support random access");
886 //! returns whether this transformation is self-inverting (e.g. xor with a keystream)
887 virtual bool IsSelfInverting() const =0;
888 //! returns whether this is an encryption object
889 virtual bool IsForwardTransformation() const =0;
892 //! interface for hash functions and data processing part of MACs
894 /*! HashTransformation objects are stateful. They are created in an initial state,
895 change state as Update() is called, and return to the initial
896 state when Final() is called. This interface allows a large message to
897 be hashed in pieces by calling Update() on each piece followed by
898 calling Final().
900 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE HashTransformation : public Algorithm
902 public:
903 //! process more input
904 virtual void Update(const byte *input, unsigned int length) =0;
906 //! request space to write input into
907 virtual byte * CreateUpdateSpace(unsigned int &size) {size=0; return NULL;}
909 //! compute hash for current message, then restart for a new message
910 /*! \pre size of digest == DigestSize(). */
911 virtual void Final(byte *digest)
912 {TruncatedFinal(digest, DigestSize());}
914 //! discard the current state, and restart with a new message
915 virtual void Restart()
916 {TruncatedFinal(NULL, 0);}
918 //! size of the hash returned by Final()
919 virtual unsigned int DigestSize() const =0;
921 //! block size of underlying compression function, or 0 if not block based
922 virtual unsigned int BlockSize() const {return 0;}
924 //! input to Update() should have length a multiple of this for optimal speed
925 virtual unsigned int OptimalBlockSize() const {return 1;}
927 //! returns how input should be aligned for optimal performance
928 virtual unsigned int OptimalDataAlignment() const {return 1;}
930 //! use this if your input is in one piece and you don't want to call Update() and Final() separately
931 virtual void CalculateDigest(byte *digest, const byte *input, unsigned int length)
932 {Update(input, length); Final(digest);}
934 //! verify that digest is a valid digest for the current message, then reinitialize the object
935 /*! Default implementation is to call Final() and do a bitwise comparison
936 between its output and digest. */
937 virtual bool Verify(const byte *digest)
938 {return TruncatedVerify(digest, DigestSize());}
940 //! use this if your input is in one piece and you don't want to call Update() and Verify() separately
941 virtual bool VerifyDigest(const byte *digest, const byte *input, unsigned int length)
942 {Update(input, length); return Verify(digest);}
944 //! truncated version of Final()
945 virtual void TruncatedFinal(byte *digest, unsigned int digestSize) =0;
947 //! truncated version of CalculateDigest()
948 virtual void CalculateTruncatedDigest(byte *digest, unsigned int digestSize, const byte *input, unsigned int length)
949 {Update(input, length); TruncatedFinal(digest, digestSize);}
951 //! truncated version of Verify()
952 virtual bool TruncatedVerify(const byte *digest, unsigned int digestLength);
954 //! truncated version of VerifyDigest()
955 virtual bool VerifyTruncatedDigest(const byte *digest, unsigned int digestLength, const byte *input, unsigned int length)
956 {Update(input, length); return TruncatedVerify(digest, digestLength);}
958 protected:
959 void ThrowIfInvalidTruncatedSize(unsigned int size) const;
962 typedef HashTransformation HashFunction;
964 template <class T>
965 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE SimpleKeyedTransformation : public T, public SimpleKeyingInterface
967 public:
968 void ThrowIfInvalidKeyLength(unsigned int length)
969 {SimpleKeyingInterface::ThrowIfInvalidKeyLength(*this, length);}
972 typedef SimpleKeyedTransformation<BlockTransformation> BlockCipher;
973 typedef SimpleKeyedTransformation<StreamTransformation> SymmetricCipher;
974 typedef SimpleKeyedTransformation<HashTransformation> MessageAuthenticationCode;
976 //! interface for random number generators
977 /*! All return values are uniformly distributed over the range specified.
979 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE RandomNumberGenerator : public Algorithm
981 public:
982 //! generate new random byte and return it
983 virtual byte GenerateByte() =0;
985 //! generate new random bit and return it
986 /*! Default implementation is to call GenerateByte() and return its parity. */
987 virtual unsigned int GenerateBit();
989 //! generate a random 32 bit word in the range min to max, inclusive
990 virtual word32 GenerateWord32(word32 a=0, word32 b=0xffffffffL);
992 //! generate random array of bytes
993 /*! Default implementation is to call GenerateByte() size times. */
994 virtual void GenerateBlock(byte *output, unsigned int size);
996 //! generate and discard n bytes
997 /*! Default implementation is to call GenerateByte() n times. */
998 virtual void DiscardBytes(unsigned int n);
1000 //! randomly shuffle the specified array, resulting permutation is uniformly distributed
1001 template <class IT> void Shuffle(IT begin, IT end)
1003 for (; begin != end; ++begin)
1004 std::iter_swap(begin, begin + GenerateWord32(0, end-begin-1));
1009 //! returns a reference that can be passed to functions that ask for a RNG but doesn't actually use it
1010 CRYPTOPP_DLL RandomNumberGenerator & NullRNG();
1012 class WaitObjectContainer;
1014 //! interface for objects that you can wait for
1016 class CRYPTOPP_NO_VTABLE Waitable
1018 public:
1019 virtual ~Waitable() {};
1021 //! maximum number of wait objects that this object can return
1022 virtual unsigned int GetMaxWaitObjectCount() const =0;
1023 //! put wait objects into container
1024 virtual void GetWaitObjects(WaitObjectContainer &container) =0;
1025 //! wait on this object
1026 /*! same as creating an empty container, calling GetWaitObjects(), and calling Wait() on the container */
1027 bool Wait(unsigned long milliseconds);
1030 //! interface for buffered transformations
1032 /*! BufferedTransformation is a generalization of BlockTransformation,
1033 StreamTransformation, and HashTransformation.
1035 A buffered transformation is an object that takes a stream of bytes
1036 as input (this may be done in stages), does some computation on them, and
1037 then places the result into an internal buffer for later retrieval. Any
1038 partial result already in the output buffer is not modified by further
1039 input.
1041 If a method takes a "blocking" parameter, and you
1042 pass "false" for it, the method will return before all input has been processed if
1043 the input cannot be processed without waiting (for network buffers to become available, for example).
1044 In this case the method will return true
1045 or a non-zero integer value. When this happens you must continue to call the method with the same
1046 parameters until it returns false or zero, before calling any other method on it or
1047 attached BufferedTransformation. The integer return value in this case is approximately
1048 the number of bytes left to be processed, and can be used to implement a progress bar.
1050 For functions that take a "propagation" parameter, propagation != 0 means pass on the signal to attached
1051 BufferedTransformation objects, with propagation decremented at each step until it reaches 0.
1052 -1 means unlimited propagation.
1054 \nosubgrouping
1056 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE BufferedTransformation : public Algorithm, public Waitable
1058 public:
1059 // placed up here for CW8
1060 static const std::string NULL_CHANNEL; // the empty string ""
1062 BufferedTransformation() : Algorithm(false) {}
1064 //! return a reference to this object
1065 /*! This function is useful for passing a temporary BufferedTransformation object to a
1066 function that takes a non-const reference. */
1067 BufferedTransformation& Ref() {return *this;}
1069 //! \name INPUT
1070 //@{
1071 //! input a byte for processing
1072 unsigned int Put(byte inByte, bool blocking=true)
1073 {return Put(&inByte, 1, blocking);}
1074 //! input multiple bytes
1075 unsigned int Put(const byte *inString, unsigned int length, bool blocking=true)
1076 {return Put2(inString, length, 0, blocking);}
1078 //! input a 16-bit word
1079 unsigned int PutWord16(word16 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
1080 //! input a 32-bit word
1081 unsigned int PutWord32(word32 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
1083 //! request space which can be written into by the caller, and then used as input to Put()
1084 /*! \param size is requested size (as a hint) for input, and size of the returned space for output */
1085 /*! \note The purpose of this method is to help avoid doing extra memory allocations. */
1086 virtual byte * CreatePutSpace(unsigned int &size) {size=0; return NULL;}
1088 virtual bool CanModifyInput() const {return false;}
1090 //! input multiple bytes that may be modified by callee
1091 unsigned int PutModifiable(byte *inString, unsigned int length, bool blocking=true)
1092 {return PutModifiable2(inString, length, 0, blocking);}
1094 bool MessageEnd(int propagation=-1, bool blocking=true)
1095 {return !!Put2(NULL, 0, propagation < 0 ? -1 : propagation+1, blocking);}
1096 unsigned int PutMessageEnd(const byte *inString, unsigned int length, int propagation=-1, bool blocking=true)
1097 {return Put2(inString, length, propagation < 0 ? -1 : propagation+1, blocking);}
1099 //! input multiple bytes for blocking or non-blocking processing
1100 /*! \param messageEnd means how many filters to signal MessageEnd to, including this one */
1101 virtual unsigned int Put2(const byte *inString, unsigned int length, int messageEnd, bool blocking) =0;
1102 //! input multiple bytes that may be modified by callee for blocking or non-blocking processing
1103 /*! \param messageEnd means how many filters to signal MessageEnd to, including this one */
1104 virtual unsigned int PutModifiable2(byte *inString, unsigned int length, int messageEnd, bool blocking)
1105 {return Put2(inString, length, messageEnd, blocking);}
1107 //! thrown by objects that have not implemented nonblocking input processing
1108 struct BlockingInputOnly : public NotImplemented
1109 {BlockingInputOnly(const std::string &s) : NotImplemented(s + ": Nonblocking input is not implemented by this object.") {}};
1110 //@}
1112 //! \name WAITING
1113 //@{
1114 unsigned int GetMaxWaitObjectCount() const;
1115 void GetWaitObjects(WaitObjectContainer &container);
1116 //@}
1118 //! \name SIGNALS
1119 //@{
1120 virtual void IsolatedInitialize(const NameValuePairs& /* parameters */) {throw NotImplemented("BufferedTransformation: this object can't be reinitialized");}
1121 virtual bool IsolatedFlush(bool hardFlush, bool blocking) =0;
1122 virtual bool IsolatedMessageSeriesEnd(bool /* blocking */) {return false;}
1124 //! initialize or reinitialize this object
1125 virtual void Initialize(const NameValuePairs &parameters=g_nullNameValuePairs, int propagation=-1);
1126 //! flush buffered input and/or output
1127 /*! \param hardFlush is used to indicate whether all data should be flushed
1128 \note Hard flushes must be used with care. It means try to process and output everything, even if
1129 there may not be enough data to complete the action. For example, hard flushing a HexDecoder would
1130 cause an error if you do it after inputing an odd number of hex encoded characters.
1131 For some types of filters, for example ZlibDecompressor, hard flushes can only
1132 be done at "synchronization points". These synchronization points are positions in the data
1133 stream that are created by hard flushes on the corresponding reverse filters, in this
1134 example ZlibCompressor. This is useful when zlib compressed data is moved across a
1135 network in packets and compression state is preserved across packets, as in the ssh2 protocol.
1137 virtual bool Flush(bool hardFlush, int propagation=-1, bool blocking=true);
1138 //! mark end of a series of messages
1139 /*! There should be a MessageEnd immediately before MessageSeriesEnd. */
1140 virtual bool MessageSeriesEnd(int propagation=-1, bool blocking=true);
1142 //! set propagation of automatically generated and transferred signals
1143 /*! propagation == 0 means do not automaticly generate signals */
1144 virtual void SetAutoSignalPropagation(int /* propagation */) {}
1147 virtual int GetAutoSignalPropagation() const {return 0;}
1148 public:
1150 //@}
1152 //! \name RETRIEVAL OF ONE MESSAGE
1153 //@{
1154 //! returns number of bytes that is currently ready for retrieval
1155 /*! All retrieval functions return the actual number of bytes
1156 retrieved, which is the lesser of the request number and
1157 MaxRetrievable(). */
1158 virtual unsigned long MaxRetrievable() const;
1160 //! returns whether any bytes are currently ready for retrieval
1161 virtual bool AnyRetrievable() const;
1163 //! try to retrieve a single byte
1164 virtual unsigned int Get(byte &outByte);
1165 //! try to retrieve multiple bytes
1166 virtual unsigned int Get(byte *outString, unsigned int getMax);
1168 //! peek at the next byte without removing it from the output buffer
1169 virtual unsigned int Peek(byte &outByte) const;
1170 //! peek at multiple bytes without removing them from the output buffer
1171 virtual unsigned int Peek(byte *outString, unsigned int peekMax) const;
1173 //! try to retrieve a 16-bit word
1174 unsigned int GetWord16(word16 &value, ByteOrder order=BIG_ENDIAN_ORDER);
1175 //! try to retrieve a 32-bit word
1176 unsigned int GetWord32(word32 &value, ByteOrder order=BIG_ENDIAN_ORDER);
1178 //! try to peek at a 16-bit word
1179 unsigned int PeekWord16(word16 &value, ByteOrder order=BIG_ENDIAN_ORDER);
1180 //! try to peek at a 32-bit word
1181 unsigned int PeekWord32(word32 &value, ByteOrder order=BIG_ENDIAN_ORDER);
1183 //! move transferMax bytes of the buffered output to target as input
1184 unsigned long TransferTo(BufferedTransformation &target, unsigned long transferMax=ULONG_MAX, const std::string &channel=NULL_CHANNEL)
1185 {TransferTo2(target, transferMax, channel); return transferMax;}
1187 //! discard skipMax bytes from the output buffer
1188 virtual unsigned long Skip(unsigned long skipMax=ULONG_MAX);
1190 //! copy copyMax bytes of the buffered output to target as input
1191 unsigned long CopyTo(BufferedTransformation &target, unsigned long copyMax=ULONG_MAX, const std::string &channel=NULL_CHANNEL) const
1192 {return CopyRangeTo(target, 0, copyMax, channel);}
1194 //! copy copyMax bytes of the buffered output, starting at position (relative to current position), to target as input
1195 unsigned long CopyRangeTo(BufferedTransformation &target, unsigned long position, unsigned long copyMax=ULONG_MAX, const std::string &channel=NULL_CHANNEL) const
1196 {unsigned long i = position; CopyRangeTo2(target, i, i+copyMax, channel); return i-position;}
1198 //@}
1200 //! \name RETRIEVAL OF MULTIPLE MESSAGES
1201 //@{
1203 virtual unsigned long TotalBytesRetrievable() const;
1204 //! number of times MessageEnd() has been received minus messages retrieved or skipped
1205 virtual unsigned int NumberOfMessages() const;
1206 //! returns true if NumberOfMessages() > 0
1207 virtual bool AnyMessages() const;
1208 //! start retrieving the next message
1210 Returns false if no more messages exist or this message
1211 is not completely retrieved.
1213 virtual bool GetNextMessage();
1214 //! skip count number of messages
1215 virtual unsigned int SkipMessages(unsigned int count=UINT_MAX);
1217 unsigned int TransferMessagesTo(BufferedTransformation &target, unsigned int count=UINT_MAX, const std::string &channel=NULL_CHANNEL)
1218 {TransferMessagesTo2(target, count, channel); return count;}
1220 unsigned int CopyMessagesTo(BufferedTransformation &target, unsigned int count=UINT_MAX, const std::string &channel=NULL_CHANNEL) const;
1223 virtual void SkipAll();
1225 void TransferAllTo(BufferedTransformation &target, const std::string &channel=NULL_CHANNEL)
1226 {TransferAllTo2(target, channel);}
1228 void CopyAllTo(BufferedTransformation &target, const std::string &channel=NULL_CHANNEL) const;
1230 virtual bool GetNextMessageSeries() {return false;}
1231 virtual unsigned int NumberOfMessagesInThisSeries() const {return NumberOfMessages();}
1232 virtual unsigned int NumberOfMessageSeries() const {return 0;}
1233 //@}
1235 //! \name NON-BLOCKING TRANSFER OF OUTPUT
1236 //@{
1237 virtual unsigned int TransferTo2(BufferedTransformation &target, unsigned long &byteCount, const std::string &channel=NULL_CHANNEL, bool blocking=true) =0;
1238 virtual unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const =0;
1239 unsigned int TransferMessagesTo2(BufferedTransformation &target, unsigned int &messageCount, const std::string &channel=NULL_CHANNEL, bool blocking=true);
1240 unsigned int TransferAllTo2(BufferedTransformation &target, const std::string &channel=NULL_CHANNEL, bool blocking=true);
1241 //@}
1243 //! \name CHANNELS
1244 //@{
1245 struct NoChannelSupport : public NotImplemented
1246 {NoChannelSupport() : NotImplemented("BufferedTransformation: this object doesn't support multiple channels") {}};
1248 unsigned int ChannelPut(const std::string &channel, byte inByte, bool blocking=true)
1249 {return ChannelPut(channel, &inByte, 1, blocking);}
1250 unsigned int ChannelPut(const std::string &channel, const byte *inString, unsigned int length, bool blocking=true)
1251 {return ChannelPut2(channel, inString, length, 0, blocking);}
1253 unsigned int ChannelPutModifiable(const std::string &channel, byte *inString, unsigned int length, bool blocking=true)
1254 {return ChannelPutModifiable2(channel, inString, length, 0, blocking);}
1256 unsigned int ChannelPutWord16(const std::string &channel, word16 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
1257 unsigned int ChannelPutWord32(const std::string &channel, word32 value, ByteOrder order=BIG_ENDIAN_ORDER, bool blocking=true);
1259 bool ChannelMessageEnd(const std::string &channel, int propagation=-1, bool blocking=true)
1260 {return !!ChannelPut2(channel, NULL, 0, propagation < 0 ? -1 : propagation+1, blocking);}
1261 unsigned int ChannelPutMessageEnd(const std::string &channel, const byte *inString, unsigned int length, int propagation=-1, bool blocking=true)
1262 {return ChannelPut2(channel, inString, length, propagation < 0 ? -1 : propagation+1, blocking);}
1264 virtual byte * ChannelCreatePutSpace(const std::string &channel, unsigned int &size);
1266 virtual unsigned int ChannelPut2(const std::string &channel, const byte *begin, unsigned int length, int messageEnd, bool blocking);
1267 virtual unsigned int ChannelPutModifiable2(const std::string &channel, byte *begin, unsigned int length, int messageEnd, bool blocking);
1269 virtual bool ChannelFlush(const std::string &channel, bool hardFlush, int propagation=-1, bool blocking=true);
1270 virtual bool ChannelMessageSeriesEnd(const std::string &channel, int propagation=-1, bool blocking=true);
1272 virtual void SetRetrievalChannel(const std::string &channel);
1273 //@}
1275 //! \name ATTACHMENT
1276 /*! Some BufferedTransformation objects (e.g. Filter objects)
1277 allow other BufferedTransformation objects to be attached. When
1278 this is done, the first object instead of buffering its output,
1279 sents that output to the attached object as input. The entire
1280 attachment chain is deleted when the anchor object is destructed.
1282 //@{
1283 //! returns whether this object allows attachment
1284 virtual bool Attachable() {return false;}
1285 //! returns the object immediately attached to this object or NULL for no attachment
1286 virtual BufferedTransformation *AttachedTransformation() {assert(!Attachable()); return 0;}
1288 virtual const BufferedTransformation *AttachedTransformation() const
1289 {return const_cast<BufferedTransformation *>(this)->AttachedTransformation();}
1290 //! delete the current attachment chain and replace it with newAttachment
1291 virtual void Detach(BufferedTransformation* /* newAttachment */ = 0)
1292 {assert(!Attachable()); throw NotImplemented("BufferedTransformation: this object is not attachable");}
1293 //! add newAttachment to the end of attachment chain
1294 virtual void Attach(BufferedTransformation *newAttachment);
1295 //@}
1297 protected:
1298 static int DecrementPropagation(int propagation)
1299 {return propagation != 0 ? propagation - 1 : 0;}
1302 //! returns a reference to a BufferedTransformation object that discards all input
1303 BufferedTransformation & TheBitBucket();
1305 //! interface for crypto material, such as public and private keys, and crypto parameters
1307 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE CryptoMaterial : public NameValuePairs
1309 public:
1310 //! exception thrown when invalid crypto material is detected
1311 class CRYPTOPP_DLL InvalidMaterial : public InvalidDataFormat
1313 public:
1314 explicit InvalidMaterial(const std::string &s) : InvalidDataFormat(s) {}
1317 //! assign values from source to this object
1318 /*! \note This function can be used to create a public key from a private key. */
1319 virtual void AssignFrom(const NameValuePairs &source) =0;
1321 //! check this object for errors
1322 /*! \param level denotes the level of thoroughness:
1323 0 - using this object won't cause a crash or exception (rng is ignored)
1324 1 - this object will probably function (encrypt, sign, etc.) correctly (but may not check for weak keys and such)
1325 2 - make sure this object will function correctly, and do reasonable security checks
1326 3 - do checks that may take a long time
1327 \return true if the tests pass */
1328 virtual bool Validate(RandomNumberGenerator &rng, unsigned int level) const =0;
1330 //! throws InvalidMaterial if this object fails Validate() test
1331 virtual void ThrowIfInvalid(RandomNumberGenerator &rng, unsigned int level) const
1332 {if (!Validate(rng, level)) throw InvalidMaterial("CryptoMaterial: this object contains invalid values");}
1334 // virtual std::vector<std::string> GetSupportedFormats(bool includeSaveOnly=false, bool includeLoadOnly=false);
1336 //! save key into a BufferedTransformation
1337 virtual void Save(BufferedTransformation& /* bt */) const
1338 {throw NotImplemented("CryptoMaterial: this object does not support saving");}
1340 //! load key from a BufferedTransformation
1341 /*! \throws KeyingErr if decode fails
1342 \note Generally does not check that the key is valid.
1343 Call ValidateKey() or ThrowIfInvalidKey() to check that. */
1344 virtual void Load(BufferedTransformation& /* bt */)
1345 {throw NotImplemented("CryptoMaterial: this object does not support loading");}
1347 //! \return whether this object supports precomputation
1348 virtual bool SupportsPrecomputation() const {return false;}
1349 //! do precomputation
1350 /*! The exact semantics of Precompute() is varies, but
1351 typically it means calculate a table of n objects
1352 that can be used later to speed up computation. */
1353 virtual void Precompute(unsigned int /* n */)
1354 {assert(!SupportsPrecomputation()); throw NotImplemented("CryptoMaterial: this object does not support precomputation");}
1355 //! retrieve previously saved precomputation
1356 virtual void LoadPrecomputation(BufferedTransformation& /* storedPrecomputation */)
1357 {assert(!SupportsPrecomputation()); throw NotImplemented("CryptoMaterial: this object does not support precomputation");}
1358 //! save precomputation for later use
1359 virtual void SavePrecomputation(BufferedTransformation& /* storedPrecomputation */) const
1360 {assert(!SupportsPrecomputation()); throw NotImplemented("CryptoMaterial: this object does not support precomputation");}
1362 // for internal library use
1363 void DoQuickSanityCheck() const {ThrowIfInvalid(NullRNG(), 0);}
1366 //! interface for generatable crypto material, such as private keys and crypto parameters
1368 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE GeneratableCryptoMaterial : virtual public CryptoMaterial
1370 public:
1371 //! generate a random key or crypto parameters
1372 /*! \throws KeyingErr if algorithm parameters are invalid, or if a key can't be generated
1373 (e.g., if this is a public key object) */
1374 virtual void GenerateRandom(RandomNumberGenerator& /* rng */, const NameValuePairs& /* params */ = g_nullNameValuePairs)
1375 {throw NotImplemented("GeneratableCryptoMaterial: this object does not support key/parameter generation");}
1377 //! calls the above function with a NameValuePairs object that just specifies "KeySize"
1378 void GenerateRandomWithKeySize(RandomNumberGenerator &rng, unsigned int keySize);
1381 //! interface for public keys
1383 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PublicKey : virtual public CryptoMaterial
1387 //! interface for private keys
1389 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PrivateKey : public GeneratableCryptoMaterial
1393 //! interface for asymmetric algorithms
1395 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE AsymmetricAlgorithm : public Algorithm
1397 public:
1398 //! returns a reference to the crypto material used by this object
1399 virtual CryptoMaterial & AccessMaterial() =0;
1400 //! returns a const reference to the crypto material used by this object
1401 virtual const CryptoMaterial & GetMaterial() const =0;
1403 //! for backwards compatibility, calls AccessMaterial().Load(bt)
1404 void BERDecode(BufferedTransformation &bt)
1405 {AccessMaterial().Load(bt);}
1406 //! for backwards compatibility, calls GetMaterial().Save(bt)
1407 void DEREncode(BufferedTransformation &bt) const
1408 {GetMaterial().Save(bt);}
1411 //! interface for asymmetric algorithms using public keys
1413 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PublicKeyAlgorithm : public AsymmetricAlgorithm
1415 public:
1416 // VC60 workaround: no co-variant return type
1417 CryptoMaterial & AccessMaterial() {return AccessPublicKey();}
1418 const CryptoMaterial & GetMaterial() const {return GetPublicKey();}
1420 virtual PublicKey & AccessPublicKey() =0;
1421 virtual const PublicKey & GetPublicKey() const {return const_cast<PublicKeyAlgorithm *>(this)->AccessPublicKey();}
1424 //! interface for asymmetric algorithms using private keys
1426 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PrivateKeyAlgorithm : public AsymmetricAlgorithm
1428 public:
1429 CryptoMaterial & AccessMaterial() {return AccessPrivateKey();}
1430 const CryptoMaterial & GetMaterial() const {return GetPrivateKey();}
1432 virtual PrivateKey & AccessPrivateKey() =0;
1433 virtual const PrivateKey & GetPrivateKey() const {return const_cast<PrivateKeyAlgorithm *>(this)->AccessPrivateKey();}
1436 /*! This class provides an interface common to encryptors and decryptors
1437 for querying their plaintext and ciphertext lengths.
1439 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_CryptoSystem
1441 public:
1442 virtual ~PK_CryptoSystem() {}
1444 //! maximum length of plaintext for a given ciphertext length
1445 /*! \note This function returns 0 if ciphertextLength is not valid (too long or too short). */
1446 virtual unsigned int MaxPlaintextLength(unsigned int ciphertextLength) const =0;
1448 //! calculate length of ciphertext given length of plaintext
1449 /*! \note This function returns 0 if plaintextLength is not valid (too long). */
1450 virtual unsigned int CiphertextLength(unsigned int plaintextLength) const =0;
1452 //! this object supports the use of the parameter with the given name
1453 /*! some possible parameter names: EncodingParameters, KeyDerivationParameters */
1454 virtual bool ParameterSupported(const char *name) const =0;
1456 //! return fixed ciphertext length, if one exists, otherwise return 0
1457 /*! \note "Fixed" here means length of ciphertext does not depend on length of plaintext.
1458 It usually does depend on the key length. */
1459 virtual unsigned int FixedCiphertextLength() const {return 0;}
1461 //! return maximum plaintext length given the fixed ciphertext length, if one exists, otherwise return 0
1462 virtual unsigned int FixedMaxPlaintextLength() const {return 0;}
1466 //! interface for public-key encryptors
1467 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Encryptor : virtual public PK_CryptoSystem, public PublicKeyAlgorithm
1469 public:
1470 //! exception thrown when trying to encrypt plaintext of invalid length
1471 class CRYPTOPP_DLL InvalidPlaintextLength : public Exception
1473 public:
1474 InvalidPlaintextLength() : Exception(OTHER_ERROR, "PK_Encryptor: invalid plaintext length") {}
1477 //! encrypt a byte string
1478 /*! \pre CiphertextLength(plaintextLength) != 0 (i.e., plaintext isn't too long)
1479 \pre size of ciphertext == CiphertextLength(plaintextLength)
1481 virtual void Encrypt(RandomNumberGenerator &rng,
1482 const byte *plaintext, unsigned int plaintextLength,
1483 byte *ciphertext, const NameValuePairs &parameters = g_nullNameValuePairs) const =0;
1485 //! create a new encryption filter
1486 /*! \note The caller is responsible for deleting the returned pointer.
1487 \note Encoding parameters should be passed in the "EP" channel.
1489 virtual BufferedTransformation * CreateEncryptionFilter(RandomNumberGenerator &rng,
1490 BufferedTransformation *attachment=NULL, const NameValuePairs &parameters = g_nullNameValuePairs) const;
1493 //! interface for public-key signers and verifiers
1495 /*! This class provides an interface common to signers and verifiers
1496 for querying scheme properties.
1498 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_SignatureScheme
1500 public:
1501 //! 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
1502 class CRYPTOPP_DLL InvalidKeyLength : public Exception
1504 public:
1505 InvalidKeyLength(const std::string &message) : Exception(OTHER_ERROR, message) {}
1508 //! 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
1509 class CRYPTOPP_DLL KeyTooShort : public InvalidKeyLength
1511 public:
1512 KeyTooShort() : InvalidKeyLength("PK_Signer: key too short for this signature scheme") {}
1515 virtual ~PK_SignatureScheme() {}
1517 //! signature length if it only depends on the key, otherwise 0
1518 virtual unsigned int SignatureLength() const =0;
1520 //! maximum signature length produced for a given length of recoverable message part
1521 virtual unsigned int MaxSignatureLength(unsigned int /* recoverablePartLength */ = 0) const {return SignatureLength();}
1523 //! length of longest message that can be recovered, or 0 if this signature scheme does not support message recovery
1524 virtual unsigned int MaxRecoverableLength() const =0;
1526 //! 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
1527 virtual unsigned int MaxRecoverableLengthFromSignatureLength(unsigned int signatureLength) const =0;
1529 //! requires a random number generator to sign
1530 /*! if this returns false, NullRNG() can be passed to functions that take RandomNumberGenerator & */
1531 virtual bool IsProbabilistic() const =0;
1533 //! whether or not a non-recoverable message part can be signed
1534 virtual bool AllowNonrecoverablePart() const =0;
1536 //! if this function returns true, during verification you must input the signature before the message, otherwise you can input it at anytime */
1537 virtual bool SignatureUpfront() const {return false;}
1539 //! whether you must input the recoverable part before the non-recoverable part during signing
1540 virtual bool RecoverablePartFirst() const =0;
1543 //! interface for accumulating messages to be signed or verified
1544 /*! Only Update() should be called
1545 on this class. No other functions inherited from HashTransformation should be called.
1547 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_MessageAccumulator : public HashTransformation
1549 public:
1550 //! should not be called on PK_MessageAccumulator
1551 unsigned int DigestSize() const
1552 {throw NotImplemented("PK_MessageAccumulator: DigestSize() should not be called");}
1553 //! should not be called on PK_MessageAccumulator
1554 void TruncatedFinal(byte* /* digest */, unsigned int /* digestSize */)
1555 {throw NotImplemented("PK_MessageAccumulator: TruncatedFinal() should not be called");}
1558 //! interface for public-key signers
1560 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Signer : public PK_SignatureScheme, public PrivateKeyAlgorithm
1562 public:
1563 //! create a new HashTransformation to accumulate the message to be signed
1564 virtual PK_MessageAccumulator * NewSignatureAccumulator(RandomNumberGenerator &rng) const =0;
1566 virtual void InputRecoverableMessage(PK_MessageAccumulator &messageAccumulator, const byte *recoverableMessage, unsigned int recoverableMessageLength) const =0;
1568 //! sign and delete messageAccumulator (even in case of exception thrown)
1569 /*! \pre size of signature == MaxSignatureLength()
1570 \return actual signature length
1572 virtual unsigned int Sign(RandomNumberGenerator &rng, PK_MessageAccumulator *messageAccumulator, byte *signature) const;
1574 //! sign and restart messageAccumulator
1575 /*! \pre size of signature == MaxSignatureLength()
1576 \return actual signature length
1578 virtual unsigned int SignAndRestart(RandomNumberGenerator &rng, PK_MessageAccumulator &messageAccumulator, byte *signature, bool restart=true) const =0;
1580 //! sign a message
1581 /*! \pre size of signature == MaxSignatureLength()
1582 \return actual signature length
1584 virtual unsigned int SignMessage(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature) const;
1586 //! sign a recoverable message
1587 /*! \pre size of signature == MaxSignatureLength(recoverableMessageLength)
1588 \return actual signature length
1590 virtual unsigned int SignMessageWithRecovery(RandomNumberGenerator &rng, const byte *recoverableMessage, unsigned int recoverableMessageLength,
1591 const byte *nonrecoverableMessage, unsigned int nonrecoverableMessageLength, byte *signature) const;
1594 //! interface for public-key signature verifiers
1595 /*! The Recover* functions throw NotImplemented if the signature scheme does not support
1596 message recovery.
1597 The Verify* functions throw InvalidDataFormat if the scheme does support message
1598 recovery and the signature contains a non-empty recoverable message part. The
1599 Recovery* functions should be used in that case.
1601 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_Verifier : public PK_SignatureScheme, public PublicKeyAlgorithm
1603 public:
1604 //! create a new HashTransformation to accumulate the message to be verified
1605 virtual PK_MessageAccumulator * NewVerificationAccumulator() const =0;
1607 //! input signature into a message accumulator
1608 virtual void InputSignature(PK_MessageAccumulator &messageAccumulator, const byte *signature, unsigned int signatureLength) const =0;
1610 //! check whether messageAccumulator contains a valid signature and message, and delete messageAccumulator (even in case of exception thrown)
1611 virtual bool Verify(PK_MessageAccumulator *messageAccumulator) const;
1613 //! check whether messageAccumulator contains a valid signature and message, and restart messageAccumulator
1614 virtual bool VerifyAndRestart(PK_MessageAccumulator &messageAccumulator) const =0;
1616 //! check whether input signature is a valid signature for input message
1617 virtual bool VerifyMessage(const byte *message, unsigned int messageLen,
1618 const byte *signature, unsigned int signatureLength) const;
1620 //! recover a message from its signature
1621 /*! \pre size of recoveredMessage == MaxRecoverableLengthFromSignatureLength(signatureLength)
1623 virtual DecodingResult Recover(byte *recoveredMessage, PK_MessageAccumulator *messageAccumulator) const;
1625 //! recover a message from its signature
1626 /*! \pre size of recoveredMessage == MaxRecoverableLengthFromSignatureLength(signatureLength)
1628 virtual DecodingResult RecoverAndRestart(byte *recoveredMessage, PK_MessageAccumulator &messageAccumulator) const =0;
1630 //! recover a message from its signature
1631 /*! \pre size of recoveredMessage == MaxRecoverableLengthFromSignatureLength(signatureLength)
1633 virtual DecodingResult RecoverMessage(byte *recoveredMessage,
1634 const byte *nonrecoverableMessage, unsigned int nonrecoverableMessageLength,
1635 const byte *signature, unsigned int signatureLength) const;
1638 //! interface for domains of authenticated key agreement protocols
1640 //! BER Decode Exception Class, may be thrown during an ASN1 BER decode operation
1641 class CRYPTOPP_DLL BERDecodeErr : public InvalidArgument
1643 public:
1644 BERDecodeErr() : InvalidArgument("BER decode error") {}
1645 BERDecodeErr(const std::string &s) : InvalidArgument(s) {}
1648 //! interface for encoding and decoding ASN1 objects
1649 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE ASN1Object
1651 public:
1652 virtual ~ASN1Object() {}
1653 //! decode this object from a BufferedTransformation, using BER (Basic Encoding Rules)
1654 virtual void BERDecode(BufferedTransformation &bt) =0;
1655 //! encode this object into a BufferedTransformation, using DER (Distinguished Encoding Rules)
1656 virtual void DEREncode(BufferedTransformation &bt) const =0;
1657 //! encode this object into a BufferedTransformation, using BER
1658 /*! this may be useful if DEREncode() would be too inefficient */
1659 virtual void BEREncode(BufferedTransformation &bt) const {DEREncode(bt);}
1662 NAMESPACE_END
1664 #endif
1665 ////////////////////////////////////////////////////////////////////////////////
1668 ////////////////////////////////////////////////////////////////////////////////
1669 #ifndef CRYPTOPP_SMARTPTR_H
1670 #define CRYPTOPP_SMARTPTR_H
1672 //- #include "config.h"
1673 #include <algorithm>
1675 NAMESPACE_BEGIN(CryptoPP)
1677 template <class T> class simple_ptr
1679 public:
1680 simple_ptr() : m_p(NULL) {}
1681 ~simple_ptr() {delete m_p;}
1682 T *m_p;
1685 template <class T> class member_ptr
1687 public:
1688 explicit member_ptr(T *p = NULL) : m_p(p) {}
1690 ~member_ptr();
1692 const T& operator*() const { return *m_p; }
1693 T& operator*() { return *m_p; }
1695 const T* operator->() const { return m_p; }
1696 T* operator->() { return m_p; }
1698 const T* get() const { return m_p; }
1699 T* get() { return m_p; }
1701 T* release()
1703 T *old_p = m_p;
1704 m_p = 0;
1705 return old_p;
1708 void reset(T *p = 0);
1710 protected:
1711 member_ptr(const member_ptr<T>& rhs); // copy not allowed
1712 void operator=(const member_ptr<T>& rhs); // assignment not allowed
1714 T *m_p;
1717 template <class T> member_ptr<T>::~member_ptr() {delete m_p;}
1718 template <class T> void member_ptr<T>::reset(T *p) {delete m_p; m_p = p;}
1720 NAMESPACE_END
1722 #endif
1723 ////////////////////////////////////////////////////////////////////////////////
1726 ////////////////////////////////////////////////////////////////////////////////
1727 #ifndef CRYPTOPP_MISC_H
1728 #define CRYPTOPP_MISC_H
1730 //- #include "cryptlib.h"
1731 //- #include "smartptr.h"
1733 #ifdef INTEL_INTRINSICS
1734 #include <stdlib.h>
1735 #endif
1737 NAMESPACE_BEGIN(CryptoPP)
1739 // ************** compile-time assertion ***************
1741 template<int>
1742 struct CompileTimeAssert;
1744 template<>
1745 struct CompileTimeAssert<true> {};
1747 #if defined(_WIN32) || defined(__CYGWIN__)
1748 #define CRYPTOPP_COMPILE_ASSERT( x )
1749 #define CRYPTOPP_COMPILE_ASSERT_GLOBAL(assertion)
1750 #define CRYPTOPP_COMPILE_ASSERT_INSTANCE(assertion, instance)
1751 #define CRYPTOPP_ASSERT_JOIN(X, Y)
1752 #define CRYPTOPP_DO_ASSERT_JOIN(X, Y)
1754 #else
1755 #define CRYPTOPP_COMPILE_ASSERT( x ) \
1756 { CompileTimeAssert<((x) != 0)> ERROR; (void)ERROR; }
1758 #define CRYPTOPP_COMPILE_ASSERT_GLOBAL(assertion) CRYPTOPP_COMPILE_ASSERT_INSTANCE(assertion, __LINE__)
1759 #if defined(CRYPTOPP_EXPORTS) || defined(CRYPTOPP_IMPORTS)
1760 #define CRYPTOPP_COMPILE_ASSERT_INSTANCE(assertion, instance)
1761 #else
1762 #define CRYPTOPP_COMPILE_ASSERT_INSTANCE(assertion, instance) \
1763 CompileTimeAssert<(assertion)> CRYPTOPP_ASSERT_JOIN(cryptopp_assert_, instance)
1764 #endif
1765 #define CRYPTOPP_ASSERT_JOIN(X, Y) CRYPTOPP_DO_ASSERT_JOIN(X, Y)
1766 #define CRYPTOPP_DO_ASSERT_JOIN(X, Y) X##Y
1767 #endif
1769 // ************** misc classes ***************
1771 class CRYPTOPP_DLL Empty
1775 //! _
1776 template <class BASE1, class BASE2>
1777 class CRYPTOPP_NO_VTABLE TwoBases : public BASE1, public BASE2
1781 template <class T>
1782 class ObjectHolder
1784 protected:
1785 T m_object;
1788 class NotCopyable
1790 public:
1791 NotCopyable() {}
1792 private:
1793 NotCopyable(const NotCopyable &);
1794 void operator=(const NotCopyable &);
1797 template <class T>
1798 struct NewObject
1800 T* operator()() const {return new T;}
1803 /*! This function safely initializes a static object in a multithreaded environment without using locks.
1804 It may leak memory when two threads try to initialize the static object at the same time
1805 but this should be acceptable since each static object is only initialized once per session.
1807 template <class T, class F = NewObject<T>, int instance=0>
1808 class Singleton
1810 public:
1811 Singleton(F objectFactory = F()) : m_objectFactory(objectFactory) {}
1813 // VC60 workaround: use "..." to prevent this function from being inlined
1814 const T & Ref(...) const;
1816 private:
1817 F m_objectFactory;
1820 template <class T, class F, int instance>
1821 const T & Singleton<T, F, instance>::Ref(...) const
1823 static simple_ptr<T> s_pObject;
1824 static char s_objectState = 0;
1826 retry:
1827 switch (s_objectState)
1829 case 0:
1830 s_objectState = 1;
1833 s_pObject.m_p = m_objectFactory();
1835 catch(...)
1837 s_objectState = 0;
1838 throw;
1840 s_objectState = 2;
1841 break;
1842 case 1:
1843 goto retry;
1844 default:
1845 break;
1847 return *s_pObject.m_p;
1850 // ************** misc functions ***************
1852 // can't use std::min or std::max in MSVC60 or Cygwin 1.1.0
1853 template <class T> inline const T& STDMIN(const T& a, const T& b)
1855 return b < a ? b : a;
1858 template <class T> inline const T& STDMAX(const T& a, const T& b)
1860 return a < b ? b : a;
1863 #define RETURN_IF_NONZERO(x) unsigned int returnedValue = x; if (returnedValue) return returnedValue
1865 // this version of the macro is fastest on Pentium 3 and Pentium 4 with MSVC 6 SP5 w/ Processor Pack
1866 #define GETBYTE(x, y) (unsigned int)byte((x)>>(8*(y)))
1867 // these may be faster on other CPUs/compilers
1868 // #define GETBYTE(x, y) (unsigned int)(((x)>>(8*(y)))&255)
1869 // #define GETBYTE(x, y) (((byte *)&(x))[y])
1871 CRYPTOPP_DLL unsigned int Parity(unsigned long);
1872 CRYPTOPP_DLL unsigned long Crop(unsigned long, unsigned int size);
1874 template <typename T>
1875 unsigned int BitPrecision(const T &value)
1877 if (!value)
1878 return 0;
1880 unsigned int l=0, h=8*sizeof(value);
1882 while (h-l > 1)
1884 unsigned int t = (l+h)/2;
1885 if (value >> t)
1886 l = t;
1887 else
1888 h = t;
1891 return h;
1894 template <typename T>
1895 unsigned int BytePrecision(const T &value)
1897 unsigned int i;
1898 for (i=sizeof(value); i; --i)
1899 if (value >> (i-1)*8)
1900 break;
1902 return i;
1905 inline unsigned int BitsToBytes(unsigned int bitCount)
1907 return ((bitCount+7)/(8));
1910 inline unsigned int BytesToWords(unsigned int byteCount)
1912 return ((byteCount+WORD_SIZE-1)/WORD_SIZE);
1915 inline unsigned int BitsToWords(unsigned int bitCount)
1917 return ((bitCount+WORD_BITS-1)/(WORD_BITS));
1920 inline unsigned int BitsToDwords(unsigned int bitCount)
1922 return ((bitCount+2*WORD_BITS-1)/(2*WORD_BITS));
1925 CRYPTOPP_DLL void xorbuf(byte *buf, const byte *mask, unsigned int count);
1926 CRYPTOPP_DLL void xorbuf(byte *output, const byte *input, const byte *mask, unsigned int count);
1928 template <class T>
1929 inline bool IsPowerOf2(T n)
1931 return n > 0 && (n & (n-1)) == 0;
1934 template <class T1, class T2>
1935 inline T2 ModPowerOf2(T1 a, T2 b)
1937 assert(IsPowerOf2(b));
1938 return T2(a) & (b-1);
1941 template <class T>
1942 inline T RoundDownToMultipleOf(T n, T m)
1944 return n - (IsPowerOf2(m) ? ModPowerOf2(n, m) : (n%m));
1947 template <class T>
1948 inline T RoundUpToMultipleOf(T n, T m)
1950 return RoundDownToMultipleOf(n+m-1, m);
1953 template <class T>
1954 inline unsigned int GetAlignment(T* /* dummy */ = NULL) // VC60 workaround
1956 #if defined(__GNUC__)
1957 return __alignof__(T);
1958 #elif defined(_MSC_VER) and (_MSC_VER >= 1300)
1959 return __alignof(T);
1960 #else
1961 return sizeof(T);
1962 #endif
1965 inline bool IsAlignedOn(const void *p, unsigned int alignment)
1967 return IsPowerOf2(alignment) ? ModPowerOf2((size_t)p, alignment) == 0 : (size_t)p % alignment == 0;
1970 template <class T>
1971 inline bool IsAligned(const void *p, T* /* dummy */ = NULL) // VC60 workaround
1973 return IsAlignedOn(p, GetAlignment<T>());
1976 #ifdef IS_LITTLE_ENDIAN
1977 typedef LittleEndian NativeByteOrder;
1978 #else
1979 typedef BigEndian NativeByteOrder;
1980 #endif
1982 inline ByteOrder GetNativeByteOrder()
1984 return NativeByteOrder::ToEnum();
1987 inline bool NativeByteOrderIs(ByteOrder order)
1989 return order == GetNativeByteOrder();
1992 template <class T> // can't use <sstream> because GCC 2.95.2 doesn't have it
1993 inline std::string IntToString(T a, unsigned int base = 10)
1995 if (a == 0)
1996 return "0";
1997 bool negate = false;
1998 if (a < 0)
2000 negate = true;
2001 a = 0-a; // VC .NET does not like -a
2003 std::string result;
2004 while (a > 0)
2006 T digit = a % base;
2007 result = char((digit < 10 ? '0' : ('a' - 10)) + digit) + result;
2008 a /= base;
2010 if (negate)
2011 result = "-" + result;
2012 return result;
2015 // Avoid warnings about compare against zero for unsigned
2016 template <> // can't use <sstream> because GCC 2.95.2 doesn't have it
2017 inline std::string IntToString<unsigned int>(unsigned int a, unsigned int base)
2019 if (a == 0)
2020 return "0";
2021 std::string result;
2022 while (a > 0)
2024 unsigned digit = a % base;
2025 result = char((digit < 10 ? '0' : ('a' - 10)) + digit) + result;
2026 a /= base;
2028 return result;
2031 template <class T1, class T2>
2032 inline T1 SaturatingSubtract(T1 a, T2 b)
2034 CRYPTOPP_COMPILE_ASSERT(T1(-1)>0); // T1 is unsigned type
2035 CRYPTOPP_COMPILE_ASSERT(T2(-1)>0); // T2 is unsigned type
2036 return T1((a > b) ? (a - b) : 0);
2039 template <class T>
2040 inline CipherDir GetCipherDir(const T &obj)
2042 return obj.IsForwardTransformation() ? ENCRYPTION : DECRYPTION;
2045 void CallNewHandler();
2047 // ************** rotate functions ***************
2049 template <class T> inline T rotlFixed(T x, unsigned int y)
2051 assert(y < sizeof(T)*8);
2052 return (x<<y) | (x>>(sizeof(T)*8-y));
2055 template <class T> inline T rotrFixed(T x, unsigned int y)
2057 assert(y < sizeof(T)*8);
2058 return (x>>y) | (x<<(sizeof(T)*8-y));
2061 template <class T> inline T rotlVariable(T x, unsigned int y)
2063 assert(y < sizeof(T)*8);
2064 return (x<<y) | (x>>(sizeof(T)*8-y));
2067 template <class T> inline T rotrVariable(T x, unsigned int y)
2069 assert(y < sizeof(T)*8);
2070 return (x>>y) | (x<<(sizeof(T)*8-y));
2073 template <class T> inline T rotlMod(T x, unsigned int y)
2075 y %= sizeof(T)*8;
2076 return (x<<y) | (x>>(sizeof(T)*8-y));
2079 template <class T> inline T rotrMod(T x, unsigned int y)
2081 y %= sizeof(T)*8;
2082 return (x>>y) | (x<<(sizeof(T)*8-y));
2085 #ifdef INTEL_INTRINSICS
2087 #pragma intrinsic(_lrotl, _lrotr)
2089 template<> inline word32 rotlFixed<word32>(word32 x, unsigned int y)
2091 assert(y < 32);
2092 return y ? _lrotl(x, y) : x;
2095 template<> inline word32 rotrFixed<word32>(word32 x, unsigned int y)
2097 assert(y < 32);
2098 return y ? _lrotr(x, y) : x;
2101 template<> inline word32 rotlVariable<word32>(word32 x, unsigned int y)
2103 assert(y < 32);
2104 return _lrotl(x, y);
2107 template<> inline word32 rotrVariable<word32>(word32 x, unsigned int y)
2109 assert(y < 32);
2110 return _lrotr(x, y);
2113 template<> inline word32 rotlMod<word32>(word32 x, unsigned int y)
2115 return _lrotl(x, y);
2118 template<> inline word32 rotrMod<word32>(word32 x, unsigned int y)
2120 return _lrotr(x, y);
2123 #endif // #ifdef INTEL_INTRINSICS
2125 #ifdef PPC_INTRINSICS
2127 template<> inline word32 rotlFixed<word32>(word32 x, unsigned int y)
2129 assert(y < 32);
2130 return y ? __rlwinm(x,y,0,31) : x;
2133 template<> inline word32 rotrFixed<word32>(word32 x, unsigned int y)
2135 assert(y < 32);
2136 return y ? __rlwinm(x,32-y,0,31) : x;
2139 template<> inline word32 rotlVariable<word32>(word32 x, unsigned int y)
2141 assert(y < 32);
2142 return (__rlwnm(x,y,0,31));
2145 template<> inline word32 rotrVariable<word32>(word32 x, unsigned int y)
2147 assert(y < 32);
2148 return (__rlwnm(x,32-y,0,31));
2151 template<> inline word32 rotlMod<word32>(word32 x, unsigned int y)
2153 return (__rlwnm(x,y,0,31));
2156 template<> inline word32 rotrMod<word32>(word32 x, unsigned int y)
2158 return (__rlwnm(x,32-y,0,31));
2161 #endif // #ifdef PPC_INTRINSICS
2163 // ************** endian reversal ***************
2165 template <class T>
2166 inline unsigned int GetByte(ByteOrder order, T value, unsigned int index)
2168 if (order == LITTLE_ENDIAN_ORDER)
2169 return GETBYTE(value, index);
2170 else
2171 return GETBYTE(value, sizeof(T)-index-1);
2174 inline byte ByteReverse(byte value)
2176 return value;
2179 inline word16 ByteReverse(word16 value)
2181 return rotlFixed(value, 8U);
2184 inline word32 ByteReverse(word32 value)
2186 #ifdef PPC_INTRINSICS
2187 // PPC: load reverse indexed instruction
2188 return (word32)__lwbrx(&value,0);
2189 #elif defined(FAST_ROTATE)
2190 // 5 instructions with rotate instruction, 9 without
2191 return (rotrFixed(value, 8U) & 0xff00ff00) | (rotlFixed(value, 8U) & 0x00ff00ff);
2192 #else
2193 // 6 instructions with rotate instruction, 8 without
2194 value = ((value & 0xFF00FF00) >> 8) | ((value & 0x00FF00FF) << 8);
2195 return rotlFixed(value, 16U);
2196 #endif
2199 #ifdef WORD64_AVAILABLE
2200 inline word64 ByteReverse(word64 value)
2202 #ifdef CRYPTOPP_SLOW_WORD64
2203 return (word64(ByteReverse(word32(value))) << 32) | ByteReverse(word32(value>>32));
2204 #else
2205 value = ((value & W64LIT(0xFF00FF00FF00FF00)) >> 8) | ((value & W64LIT(0x00FF00FF00FF00FF)) << 8);
2206 value = ((value & W64LIT(0xFFFF0000FFFF0000)) >> 16) | ((value & W64LIT(0x0000FFFF0000FFFF)) << 16);
2207 return rotlFixed(value, 32U);
2208 #endif
2210 #endif
2212 inline byte BitReverse(byte value)
2214 value = ((value & 0xAA) >> 1) | ((value & 0x55) << 1);
2215 value = ((value & 0xCC) >> 2) | ((value & 0x33) << 2);
2216 return rotlFixed(value, 4);
2219 inline word16 BitReverse(word16 value)
2221 value = ((value & 0xAAAA) >> 1) | ((value & 0x5555) << 1);
2222 value = ((value & 0xCCCC) >> 2) | ((value & 0x3333) << 2);
2223 value = ((value & 0xF0F0) >> 4) | ((value & 0x0F0F) << 4);
2224 return ByteReverse(value);
2227 inline word32 BitReverse(word32 value)
2229 value = ((value & 0xAAAAAAAA) >> 1) | ((value & 0x55555555) << 1);
2230 value = ((value & 0xCCCCCCCC) >> 2) | ((value & 0x33333333) << 2);
2231 value = ((value & 0xF0F0F0F0) >> 4) | ((value & 0x0F0F0F0F) << 4);
2232 return ByteReverse(value);
2235 #ifdef WORD64_AVAILABLE
2236 inline word64 BitReverse(word64 value)
2238 #ifdef CRYPTOPP_SLOW_WORD64
2239 return (word64(BitReverse(word32(value))) << 32) | BitReverse(word32(value>>32));
2240 #else
2241 value = ((value & W64LIT(0xAAAAAAAAAAAAAAAA)) >> 1) | ((value & W64LIT(0x5555555555555555)) << 1);
2242 value = ((value & W64LIT(0xCCCCCCCCCCCCCCCC)) >> 2) | ((value & W64LIT(0x3333333333333333)) << 2);
2243 value = ((value & W64LIT(0xF0F0F0F0F0F0F0F0)) >> 4) | ((value & W64LIT(0x0F0F0F0F0F0F0F0F)) << 4);
2244 return ByteReverse(value);
2245 #endif
2247 #endif
2249 template <class T>
2250 inline T BitReverse(T value)
2252 if (sizeof(T) == 1)
2253 return (T)BitReverse((byte)value);
2254 else if (sizeof(T) == 2)
2255 return (T)BitReverse((word16)value);
2256 else if (sizeof(T) == 4)
2257 return (T)BitReverse((word32)value);
2258 else
2260 #ifdef WORD64_AVAILABLE
2261 assert(sizeof(T) == 8);
2262 return (T)BitReverse((word64)value);
2263 #else
2264 assert(false);
2265 return 0;
2266 #endif
2270 template <class T>
2271 inline T ConditionalByteReverse(ByteOrder order, T value)
2273 return NativeByteOrderIs(order) ? value : ByteReverse(value);
2276 template <class T>
2277 void ByteReverse(T *out, const T *in, unsigned int byteCount)
2279 assert(byteCount % sizeof(T) == 0);
2280 unsigned int count = byteCount/sizeof(T);
2281 for (unsigned int i=0; i<count; i++)
2282 out[i] = ByteReverse(in[i]);
2285 template <class T>
2286 inline void ConditionalByteReverse(ByteOrder order, T *out, const T *in, unsigned int byteCount)
2288 if (!NativeByteOrderIs(order))
2289 ByteReverse(out, in, byteCount);
2290 else if (in != out)
2291 memcpy(out, in, byteCount);
2294 template <class T>
2295 inline void GetUserKey(ByteOrder order, T *out, unsigned int outlen, const byte *in, unsigned int inlen)
2297 const unsigned int U = sizeof(T);
2298 assert(inlen <= outlen*U);
2299 memcpy(out, in, inlen);
2300 memset((byte *)out+inlen, 0, outlen*U-inlen);
2301 ConditionalByteReverse(order, out, out, RoundUpToMultipleOf(inlen, U));
2304 inline byte UnalignedGetWordNonTemplate(ByteOrder /*order*/, const byte *block, byte*)
2306 return block[0];
2309 inline word16 UnalignedGetWordNonTemplate(ByteOrder order, const byte *block, word16*)
2311 return (order == BIG_ENDIAN_ORDER)
2312 ? block[1] | (block[0] << 8)
2313 : block[0] | (block[1] << 8);
2316 inline word32 UnalignedGetWordNonTemplate(ByteOrder order, const byte *block, word32*)
2318 return (order == BIG_ENDIAN_ORDER)
2319 ? word32(block[3]) | (word32(block[2]) << 8) | (word32(block[1]) << 16) | (word32(block[0]) << 24)
2320 : word32(block[0]) | (word32(block[1]) << 8) | (word32(block[2]) << 16) | (word32(block[3]) << 24);
2323 #ifdef WORD64_AVAILABLE
2324 inline word64 UnalignedGetWordNonTemplate(ByteOrder order, const byte *block, word64*)
2326 return (order == BIG_ENDIAN_ORDER)
2328 (word64(block[7]) |
2329 (word64(block[6]) << 8) |
2330 (word64(block[5]) << 16) |
2331 (word64(block[4]) << 24) |
2332 (word64(block[3]) << 32) |
2333 (word64(block[2]) << 40) |
2334 (word64(block[1]) << 48) |
2335 (word64(block[0]) << 56))
2337 (word64(block[0]) |
2338 (word64(block[1]) << 8) |
2339 (word64(block[2]) << 16) |
2340 (word64(block[3]) << 24) |
2341 (word64(block[4]) << 32) |
2342 (word64(block[5]) << 40) |
2343 (word64(block[6]) << 48) |
2344 (word64(block[7]) << 56));
2346 #endif
2348 template <class T>
2349 inline T UnalignedGetWord(ByteOrder order, const byte *block, T*dummy=NULL)
2351 return UnalignedGetWordNonTemplate(order, block, dummy);
2354 inline void UnalignedPutWord(ByteOrder /*order*/, byte *block, byte value, const byte *xorBlock = NULL)
2356 block[0] = xorBlock ? (value ^ xorBlock[0]) : value;
2359 inline void UnalignedPutWord(ByteOrder order, byte *block, word16 value, const byte *xorBlock = NULL)
2361 if (order == BIG_ENDIAN_ORDER)
2363 block[0] = GETBYTE(value, 1);
2364 block[1] = GETBYTE(value, 0);
2366 else
2368 block[0] = GETBYTE(value, 0);
2369 block[1] = GETBYTE(value, 1);
2372 if (xorBlock)
2374 block[0] ^= xorBlock[0];
2375 block[1] ^= xorBlock[1];
2379 inline void UnalignedPutWord(ByteOrder order, byte *block, word32 value, const byte *xorBlock = NULL)
2381 if (order == BIG_ENDIAN_ORDER)
2383 block[0] = GETBYTE(value, 3);
2384 block[1] = GETBYTE(value, 2);
2385 block[2] = GETBYTE(value, 1);
2386 block[3] = GETBYTE(value, 0);
2388 else
2390 block[0] = GETBYTE(value, 0);
2391 block[1] = GETBYTE(value, 1);
2392 block[2] = GETBYTE(value, 2);
2393 block[3] = GETBYTE(value, 3);
2396 if (xorBlock)
2398 block[0] ^= xorBlock[0];
2399 block[1] ^= xorBlock[1];
2400 block[2] ^= xorBlock[2];
2401 block[3] ^= xorBlock[3];
2405 #ifdef WORD64_AVAILABLE
2406 inline void UnalignedPutWord(ByteOrder order, byte *block, word64 value, const byte *xorBlock = NULL)
2408 if (order == BIG_ENDIAN_ORDER)
2410 block[0] = GETBYTE(value, 7);
2411 block[1] = GETBYTE(value, 6);
2412 block[2] = GETBYTE(value, 5);
2413 block[3] = GETBYTE(value, 4);
2414 block[4] = GETBYTE(value, 3);
2415 block[5] = GETBYTE(value, 2);
2416 block[6] = GETBYTE(value, 1);
2417 block[7] = GETBYTE(value, 0);
2419 else
2421 block[0] = GETBYTE(value, 0);
2422 block[1] = GETBYTE(value, 1);
2423 block[2] = GETBYTE(value, 2);
2424 block[3] = GETBYTE(value, 3);
2425 block[4] = GETBYTE(value, 4);
2426 block[5] = GETBYTE(value, 5);
2427 block[6] = GETBYTE(value, 6);
2428 block[7] = GETBYTE(value, 7);
2431 if (xorBlock)
2433 block[0] ^= xorBlock[0];
2434 block[1] ^= xorBlock[1];
2435 block[2] ^= xorBlock[2];
2436 block[3] ^= xorBlock[3];
2437 block[4] ^= xorBlock[4];
2438 block[5] ^= xorBlock[5];
2439 block[6] ^= xorBlock[6];
2440 block[7] ^= xorBlock[7];
2443 #endif
2445 template <class T>
2446 inline T GetWord(bool assumeAligned, ByteOrder order, const byte *block)
2448 if (assumeAligned)
2450 assert(IsAligned<T>(block));
2451 return ConditionalByteReverse(order, *reinterpret_cast<const T *>(block));
2453 else
2454 return UnalignedGetWord<T>(order, block);
2457 template <class T>
2458 inline void GetWord(bool assumeAligned, ByteOrder order, T &result, const byte *block)
2460 result = GetWord<T>(assumeAligned, order, block);
2463 template <class T>
2464 inline void PutWord(bool assumeAligned, ByteOrder order, byte *block, T value, const byte *xorBlock = NULL)
2466 if (assumeAligned)
2468 assert(IsAligned<T>(block));
2469 if (xorBlock)
2470 *reinterpret_cast<T *>(block) = ConditionalByteReverse(order, value) ^ *reinterpret_cast<const T *>(xorBlock);
2471 else
2472 *reinterpret_cast<T *>(block) = ConditionalByteReverse(order, value);
2474 else
2475 UnalignedPutWord(order, block, value, xorBlock);
2478 template <class T, class B, bool A=true>
2479 class GetBlock
2481 public:
2482 GetBlock(const void *block)
2483 : m_block((const byte *)block) {}
2485 template <class U>
2486 inline GetBlock<T, B, A> & operator()(U &x)
2488 CRYPTOPP_COMPILE_ASSERT(sizeof(U) >= sizeof(T));
2489 x = GetWord<T>(A, B::ToEnum(), m_block);
2490 m_block += sizeof(T);
2491 return *this;
2494 private:
2495 const byte *m_block;
2498 // ************** help remove warning on g++ ***************
2500 template <bool overflow> struct SafeShifter;
2502 template<> struct SafeShifter<true>
2504 template <class T>
2505 static inline T RightShift(T /* value */, unsigned int /* bits */)
2507 return 0;
2510 template <class T>
2511 static inline T LeftShift(T /* value */, unsigned int /* bits */)
2513 return 0;
2517 template<> struct SafeShifter<false>
2519 template <class T>
2520 static inline T RightShift(T value, unsigned int bits)
2522 return value >> bits;
2525 template <class T>
2526 static inline T LeftShift(T value, unsigned int bits)
2528 return value << bits;
2532 template <unsigned int bits, class T>
2533 inline T SafeRightShift(T value)
2535 return SafeShifter<(bits>=(8*sizeof(T)))>::RightShift(value, bits);
2538 template <unsigned int bits, class T>
2539 inline T SafeLeftShift(T value)
2541 return SafeShifter<(bits>=(8*sizeof(T)))>::LeftShift(value, bits);
2544 NAMESPACE_END
2546 #endif // MISC_H
2547 ////////////////////////////////////////////////////////////////////////////////
2551 ////////////////////////////////////////////////////////////////////////////////
2552 // secblock.h - written and placed in the public domain by Wei Dai
2554 #ifndef CRYPTOPP_SECBLOCK_H
2555 #define CRYPTOPP_SECBLOCK_H
2557 //- #include "config.h"
2558 //- #include "misc.h"
2559 #include <string.h> // CodeWarrior doesn't have memory.h
2560 #include <assert.h>
2562 NAMESPACE_BEGIN(CryptoPP)
2564 // ************** secure memory allocation ***************
2566 template<class T>
2567 class AllocatorBase
2569 public:
2570 typedef T value_type;
2571 typedef size_t size_type;
2572 #ifdef CRYPTOPP_MSVCRT6
2573 typedef ptrdiff_t difference_type;
2574 #else
2575 typedef std::ptrdiff_t difference_type;
2576 #endif
2577 typedef T * pointer;
2578 typedef const T * const_pointer;
2579 typedef T & reference;
2580 typedef const T & const_reference;
2582 pointer address(reference r) const {return (&r);}
2583 const_pointer address(const_reference r) const {return (&r); }
2584 void construct(pointer p, const T& val) {new (p) T(val);}
2585 void destroy(pointer p) {p->~T();}
2586 size_type max_size() const {return ~size_type(0)/sizeof(T);} // switch to std::numeric_limits<T>::max later
2588 protected:
2589 static void CheckSize(size_t n)
2591 if (n > ~size_t(0) / sizeof(T))
2592 throw InvalidArgument("AllocatorBase: requested size would cause integer overflow");
2596 #define CRYPTOPP_INHERIT_ALLOCATOR_TYPES \
2597 typedef typename AllocatorBase<T>::value_type value_type;\
2598 typedef typename AllocatorBase<T>::size_type size_type;\
2599 typedef typename AllocatorBase<T>::difference_type difference_type;\
2600 typedef typename AllocatorBase<T>::pointer pointer;\
2601 typedef typename AllocatorBase<T>::const_pointer const_pointer;\
2602 typedef typename AllocatorBase<T>::reference reference;\
2603 typedef typename AllocatorBase<T>::const_reference const_reference;
2605 template <class T, class A>
2606 typename A::pointer StandardReallocate(A& a, T *p, typename A::size_type oldSize, typename A::size_type newSize, bool preserve)
2608 if (oldSize == newSize)
2609 return p;
2611 if (preserve)
2613 A b;
2614 typename A::pointer newPointer = b.allocate(newSize, NULL);
2615 memcpy(newPointer, p, sizeof(T)*STDMIN(oldSize, newSize));
2616 a.deallocate(p, oldSize);
2617 std::swap(a, b);
2618 return newPointer;
2620 else
2622 a.deallocate(p, oldSize);
2623 return a.allocate(newSize, NULL);
2627 template <class T>
2628 class AllocatorWithCleanup : public AllocatorBase<T>
2630 public:
2631 CRYPTOPP_INHERIT_ALLOCATOR_TYPES
2633 pointer allocate(size_type n, const void * = NULL)
2635 CheckSize(n);
2636 if (n == 0)
2637 return NULL;
2638 return new T[n];
2641 void deallocate(void *p, size_type n)
2643 memset(p, 0, n*sizeof(T));
2644 delete [] (T *)p;
2647 pointer reallocate(T *p, size_type oldSize, size_type newSize, bool preserve)
2649 return StandardReallocate(*this, p, oldSize, newSize, preserve);
2652 // VS.NET STL enforces the policy of "All STL-compliant allocators have to provide a
2653 // template class member called rebind".
2654 template <class U> struct rebind { typedef AllocatorWithCleanup<U> other; };
2657 template <class T>
2658 class NullAllocator : public AllocatorBase<T>
2660 public:
2661 CRYPTOPP_INHERIT_ALLOCATOR_TYPES
2663 pointer allocate(size_type /* n */, const void * = NULL)
2665 assert(false);
2666 return NULL;
2669 void deallocate(void* /* p */, size_type /* n */)
2671 assert(false);
2674 size_type max_size() const {return 0;}
2677 // This allocator can't be used with standard collections because
2678 // they require that all objects of the same allocator type are equivalent.
2679 // So this is for use with SecBlock only.
2680 template <class T, size_t S, class A = NullAllocator<T> >
2681 class FixedSizeAllocatorWithCleanup : public AllocatorBase<T>
2683 public:
2684 CRYPTOPP_INHERIT_ALLOCATOR_TYPES
2686 FixedSizeAllocatorWithCleanup() : m_allocated(false) {}
2688 pointer allocate(size_type n)
2690 if (n <= S && !m_allocated)
2692 m_allocated = true;
2693 return m_array;
2695 else
2696 return m_fallbackAllocator.allocate(n);
2699 pointer allocate(size_type n, const void *hint)
2701 if (n <= S && !m_allocated)
2703 m_allocated = true;
2704 return m_array;
2706 else
2707 return m_fallbackAllocator.allocate(n, hint);
2710 void deallocate(void *p, size_type n)
2712 if (p == m_array)
2714 assert(n <= S);
2715 assert(m_allocated);
2716 m_allocated = false;
2717 memset(p, 0, n*sizeof(T));
2719 else
2720 m_fallbackAllocator.deallocate(p, n);
2723 pointer reallocate(pointer p, size_type oldSize, size_type newSize, bool preserve)
2725 if (p == m_array && newSize <= S)
2727 assert(oldSize <= S);
2728 if (oldSize > newSize)
2729 memset(p + newSize, 0, (oldSize-newSize)*sizeof(T));
2730 return p;
2733 pointer newPointer = allocate(newSize, NULL);
2734 if (preserve)
2735 memcpy(newPointer, p, sizeof(T)*STDMIN(oldSize, newSize));
2736 deallocate(p, oldSize);
2737 return newPointer;
2740 size_type max_size() const {return STDMAX(m_fallbackAllocator.max_size(), S);}
2742 private:
2743 T m_array[S];
2744 A m_fallbackAllocator;
2745 bool m_allocated;
2748 //! a block of memory allocated using A
2749 template <class T, class A = AllocatorWithCleanup<T> >
2750 class SecBlock
2752 public:
2753 explicit SecBlock(unsigned int blocksize=0)
2754 : m_size(blocksize) {m_ptr = m_alloc.allocate(blocksize, NULL);}
2755 SecBlock(const SecBlock<T, A> &t)
2756 : m_size(t.m_size) {m_ptr = m_alloc.allocate(m_size, NULL); memcpy(m_ptr, t.m_ptr, m_size*sizeof(T));}
2757 SecBlock(const T *t, unsigned int len)
2758 : m_size(len)
2760 m_ptr = m_alloc.allocate(len, NULL);
2761 if (t == NULL)
2762 memset(m_ptr, 0, len*sizeof(T));
2763 else
2764 memcpy(m_ptr, t, len*sizeof(T));
2767 ~SecBlock()
2768 {m_alloc.deallocate(m_ptr, m_size);}
2770 operator const void *() const
2771 {return m_ptr;}
2772 operator void *()
2773 {return m_ptr;}
2774 #if defined(__GNUC__) && __GNUC__ < 3 // reduce warnings
2775 operator const void *()
2776 {return m_ptr;}
2777 #endif
2779 operator const T *() const
2780 {return m_ptr;}
2781 operator T *()
2782 {return m_ptr;}
2783 #if defined(__GNUC__) && __GNUC__ < 3 // reduce warnings
2784 operator const T *()
2785 {return m_ptr;}
2786 #endif
2788 template <typename I>
2789 T *operator +(I offset)
2790 {return m_ptr+offset;}
2792 template <typename I>
2793 const T *operator +(I offset) const
2794 {return m_ptr+offset;}
2796 template <typename I>
2797 T& operator[](I index)
2798 {assert((unsigned int)index < m_size); return m_ptr[index];}
2800 template <typename I>
2801 const T& operator[](I index) const
2802 {assert((unsigned int)index < m_size); return m_ptr[index];}
2804 typedef typename A::value_type value_type;
2805 typedef typename A::pointer iterator;
2806 typedef typename A::const_pointer const_iterator;
2807 typedef typename A::size_type size_type;
2809 iterator begin()
2810 {return m_ptr;}
2811 const_iterator begin() const
2812 {return m_ptr;}
2813 iterator end()
2814 {return m_ptr+m_size;}
2815 const_iterator end() const
2816 {return m_ptr+m_size;}
2818 typename A::pointer data() {return m_ptr;}
2819 typename A::const_pointer data() const {return m_ptr;}
2821 size_type size() const {return m_size;}
2822 bool empty() const {return m_size == 0;}
2824 void Assign(const T *t, unsigned int len)
2826 New(len);
2827 memcpy(m_ptr, t, len*sizeof(T));
2830 void Assign(const SecBlock<T, A> &t)
2832 New(t.m_size);
2833 memcpy(m_ptr, t.m_ptr, m_size*sizeof(T));
2836 SecBlock& operator=(const SecBlock<T, A> &t)
2838 Assign(t);
2839 return *this;
2842 bool operator==(const SecBlock<T, A> &t) const
2844 return m_size == t.m_size && memcmp(m_ptr, t.m_ptr, m_size*sizeof(T)) == 0;
2847 bool operator!=(const SecBlock<T, A> &t) const
2849 return !operator==(t);
2852 void New(unsigned int newSize)
2854 m_ptr = m_alloc.reallocate(m_ptr, m_size, newSize, false);
2855 m_size = newSize;
2858 void CleanNew(unsigned int newSize)
2860 New(newSize);
2861 memset(m_ptr, 0, m_size*sizeof(T));
2864 void Grow(unsigned int newSize)
2866 if (newSize > m_size)
2868 m_ptr = m_alloc.reallocate(m_ptr, m_size, newSize, true);
2869 m_size = newSize;
2873 void CleanGrow(unsigned int newSize)
2875 if (newSize > m_size)
2877 m_ptr = m_alloc.reallocate(m_ptr, m_size, newSize, true);
2878 memset(m_ptr+m_size, 0, (newSize-m_size)*sizeof(T));
2879 m_size = newSize;
2883 void resize(unsigned int newSize)
2885 m_ptr = m_alloc.reallocate(m_ptr, m_size, newSize, true);
2886 m_size = newSize;
2889 void swap(SecBlock<T, A> &b)
2891 std::swap(m_alloc, b.m_alloc);
2892 std::swap(m_size, b.m_size);
2893 std::swap(m_ptr, b.m_ptr);
2896 //private:
2897 A m_alloc;
2898 unsigned int m_size;
2899 T *m_ptr;
2902 typedef SecBlock<byte> SecByteBlock;
2903 typedef SecBlock<word> SecWordBlock;
2905 template <class T, unsigned int S, class A = FixedSizeAllocatorWithCleanup<T, S> >
2906 class FixedSizeSecBlock : public SecBlock<T, A>
2908 public:
2909 explicit FixedSizeSecBlock() : SecBlock<T, A>(S) {}
2912 template<class T, class U>
2913 inline bool operator==(const CryptoPP::AllocatorWithCleanup<T>&, const CryptoPP::AllocatorWithCleanup<U>&) {return (true);}
2914 template<class T, class U>
2915 inline bool operator!=(const CryptoPP::AllocatorWithCleanup<T>&, const CryptoPP::AllocatorWithCleanup<U>&) {return (false);}
2917 NAMESPACE_END
2919 NAMESPACE_BEGIN(std)
2920 template <class T, class A>
2921 inline void swap(CryptoPP::SecBlock<T, A> &a, CryptoPP::SecBlock<T, A> &b)
2923 a.swap(b);
2926 #if defined(_STLPORT_VERSION) && !defined(_STLP_MEMBER_TEMPLATE_CLASSES)
2927 template <class _Tp1, class _Tp2>
2928 inline CryptoPP::AllocatorWithCleanup<_Tp2>&
2929 __stl_alloc_rebind(CryptoPP::AllocatorWithCleanup<_Tp1>& __a, const _Tp2*)
2931 return (CryptoPP::AllocatorWithCleanup<_Tp2>&)(__a);
2933 #endif
2935 NAMESPACE_END
2937 #endif
2938 ////////////////////////////////////////////////////////////////////////////////
2942 ////////////////////////////////////////////////////////////////////////////////
2943 #ifndef CRYPTOPP_INTEGER_H
2944 #define CRYPTOPP_INTEGER_H
2946 /** \file */
2948 //- #include "cryptlib.h"
2949 //- #include "secblock.h"
2951 #include <iosfwd>
2952 #include <algorithm>
2954 #ifdef CRYPTOPP_X86ASM_AVAILABLE
2956 #ifdef _M_IX86
2957 #if (defined(__INTEL_COMPILER) && (__INTEL_COMPILER >= 500)) || (defined(__ICL) && (__ICL >= 500))
2958 #define SSE2_INTRINSICS_AVAILABLE
2959 #define CRYPTOPP_MM_MALLOC_AVAILABLE
2960 #elif defined(_MSC_VER)
2961 // _mm_free seems to be the only way to tell if the Processor Pack is installed or not
2962 #include <malloc.h>
2963 #if defined(_mm_free)
2964 #define SSE2_INTRINSICS_AVAILABLE
2965 #define CRYPTOPP_MM_MALLOC_AVAILABLE
2966 #endif
2967 #endif
2968 #endif
2970 // SSE2 intrinsics work in GCC 3.3 or later
2971 #if defined(__SSE2__) && (__GNUC__ > 3 || __GNUC_MINOR__ > 2)
2972 #define SSE2_INTRINSICS_AVAILABLE
2973 #endif
2975 #endif
2977 NAMESPACE_BEGIN(CryptoPP)
2979 #if defined(SSE2_INTRINSICS_AVAILABLE)
2980 template <class T>
2981 class AlignedAllocator : public AllocatorBase<T>
2983 public:
2984 CRYPTOPP_INHERIT_ALLOCATOR_TYPES
2986 pointer allocate(size_type n, const void *);
2987 void deallocate(void *p, size_type n);
2988 pointer reallocate(T *p, size_type oldSize, size_type newSize, bool preserve)
2990 return StandardReallocate(*this, p, oldSize, newSize, preserve);
2993 #if !(defined(CRYPTOPP_MALLOC_ALIGNMENT_IS_16) || defined(CRYPTOPP_MEMALIGN_AVAILABLE) || defined(CRYPTOPP_MM_MALLOC_AVAILABLE))
2994 #define CRYPTOPP_NO_ALIGNED_ALLOC
2995 AlignedAllocator() : m_pBlock(NULL) {}
2996 protected:
2997 void *m_pBlock;
2998 #endif
3001 template class CRYPTOPP_DLL AlignedAllocator<word>;
3002 typedef SecBlock<word, AlignedAllocator<word> > SecAlignedWordBlock;
3003 #else
3004 typedef SecWordBlock SecAlignedWordBlock;
3005 #endif
3007 void CRYPTOPP_DLL DisableSSE2();
3009 //! multiple precision integer and basic arithmetics
3010 /*! This class can represent positive and negative integers
3011 with absolute value less than (256**sizeof(word)) ** (256**sizeof(int)).
3012 \nosubgrouping
3014 class CRYPTOPP_DLL Integer : public ASN1Object
3016 public:
3017 //! \name ENUMS, EXCEPTIONS, and TYPEDEFS
3018 //@{
3019 //! division by zero exception
3020 class DivideByZero : public Exception
3022 public:
3023 DivideByZero() : Exception(OTHER_ERROR, "Integer: division by zero") {}
3027 class RandomNumberNotFound : public Exception
3029 public:
3030 RandomNumberNotFound() : Exception(OTHER_ERROR, "Integer: no integer satisfies the given parameters") {}
3034 enum Sign {POSITIVE=0, NEGATIVE=1};
3037 enum Signedness {
3039 UNSIGNED,
3041 SIGNED};
3044 enum RandomNumberType {
3046 ANY,
3048 PRIME};
3049 //@}
3051 //! \name CREATORS
3052 //@{
3053 //! creates the zero integer
3054 Integer();
3056 //! copy constructor
3057 Integer(const Integer& t);
3059 //! convert from signed long
3060 Integer(signed long value);
3062 //! convert from lword
3063 Integer(Sign s, lword value);
3065 //! convert from two words
3066 Integer(Sign s, word highWord, word lowWord);
3068 //! convert from string
3069 /*! str can be in base 2, 8, 10, or 16. Base is determined by a
3070 case insensitive suffix of 'h', 'o', or 'b'. No suffix means base 10.
3072 explicit Integer(const char *str);
3073 explicit Integer(const wchar_t *str);
3075 //! convert from big-endian byte array
3076 Integer(const byte *encodedInteger, unsigned int byteCount, Signedness s=UNSIGNED);
3078 //! convert from big-endian form stored in a BufferedTransformation
3079 Integer(BufferedTransformation &bt, unsigned int byteCount, Signedness s=UNSIGNED);
3081 //! convert from BER encoded byte array stored in a BufferedTransformation object
3082 explicit Integer(BufferedTransformation &bt);
3084 //! create a random integer
3085 /*! The random integer created is uniformly distributed over [0, 2**bitcount). */
3086 Integer(RandomNumberGenerator &rng, unsigned int bitcount);
3088 //! avoid calling constructors for these frequently used integers
3089 static const Integer &Zero();
3090 //! avoid calling constructors for these frequently used integers
3091 static const Integer &One();
3092 //! avoid calling constructors for these frequently used integers
3093 static const Integer &Two();
3095 //! create a random integer of special type
3096 /*! Ideally, the random integer created should be uniformly distributed
3097 over {x | min <= x <= max and x is of rnType and x % mod == equiv}.
3098 However the actual distribution may not be uniform because sequential
3099 search is used to find an appropriate number from a random starting
3100 point.
3101 May return (with very small probability) a pseudoprime when a prime
3102 is requested and max > lastSmallPrime*lastSmallPrime (lastSmallPrime
3103 is declared in nbtheory.h).
3104 \throw RandomNumberNotFound if the set is empty.
3106 Integer(RandomNumberGenerator &rng, const Integer &min, const Integer &max, RandomNumberType rnType=ANY, const Integer &equiv=Zero(), const Integer &mod=One());
3108 //! return the integer 2**e
3109 static Integer Power2(unsigned int e);
3110 //@}
3112 //! \name ENCODE/DECODE
3113 //@{
3114 //! minimum number of bytes to encode this integer
3115 /*! MinEncodedSize of 0 is 1 */
3116 unsigned int MinEncodedSize(Signedness=UNSIGNED) const;
3117 //! encode in big-endian format
3118 /*! unsigned means encode absolute value, signed means encode two's complement if negative.
3119 if outputLen < MinEncodedSize, the most significant bytes will be dropped
3120 if outputLen > MinEncodedSize, the most significant bytes will be padded
3122 unsigned int Encode(byte *output, unsigned int outputLen, Signedness=UNSIGNED) const;
3124 unsigned int Encode(BufferedTransformation &bt, unsigned int outputLen, Signedness=UNSIGNED) const;
3126 //! encode using Distinguished Encoding Rules, put result into a BufferedTransformation object
3127 void DEREncode(BufferedTransformation &bt) const;
3129 //! encode absolute value as big-endian octet string
3130 void DEREncodeAsOctetString(BufferedTransformation &bt, unsigned int length) const;
3132 //! encode absolute value in OpenPGP format, return length of output
3133 unsigned int OpenPGPEncode(byte *output, unsigned int bufferSize) const;
3134 //! encode absolute value in OpenPGP format, put result into a BufferedTransformation object
3135 unsigned int OpenPGPEncode(BufferedTransformation &bt) const;
3138 void Decode(const byte *input, unsigned int inputLen, Signedness=UNSIGNED);
3139 //!
3140 //* Precondition: bt.MaxRetrievable() >= inputLen
3141 void Decode(BufferedTransformation &bt, unsigned int inputLen, Signedness=UNSIGNED);
3144 void BERDecode(const byte *input, unsigned int inputLen);
3146 void BERDecode(BufferedTransformation &bt);
3148 //! decode nonnegative value as big-endian octet string
3149 void BERDecodeAsOctetString(BufferedTransformation &bt, unsigned int length);
3151 class OpenPGPDecodeErr : public Exception
3153 public:
3154 OpenPGPDecodeErr() : Exception(INVALID_DATA_FORMAT, "OpenPGP decode error") {}
3158 void OpenPGPDecode(const byte *input, unsigned int inputLen);
3160 void OpenPGPDecode(BufferedTransformation &bt);
3161 //@}
3163 //! \name ACCESSORS
3164 //@{
3165 //! return true if *this can be represented as a signed long
3166 bool IsConvertableToLong() const;
3167 //! return equivalent signed long if possible, otherwise undefined
3168 signed long ConvertToLong() const;
3170 //! number of significant bits = floor(log2(abs(*this))) + 1
3171 unsigned int BitCount() const;
3172 //! number of significant bytes = ceiling(BitCount()/8)
3173 unsigned int ByteCount() const;
3174 //! number of significant words = ceiling(ByteCount()/sizeof(word))
3175 unsigned int WordCount() const;
3177 //! return the i-th bit, i=0 being the least significant bit
3178 bool GetBit(unsigned int i) const;
3179 //! return the i-th byte
3180 byte GetByte(unsigned int i) const;
3181 //! return n lowest bits of *this >> i
3182 unsigned long GetBits(unsigned int i, unsigned int n) const;
3185 bool IsZero() const {return !*this;}
3187 bool NotZero() const {return !IsZero();}
3189 bool IsNegative() const {return sign == NEGATIVE;}
3191 bool NotNegative() const {return !IsNegative();}
3193 bool IsPositive() const {return NotNegative() && NotZero();}
3195 bool NotPositive() const {return !IsPositive();}
3197 bool IsEven() const {return GetBit(0) == 0;}
3199 bool IsOdd() const {return GetBit(0) == 1;}
3200 //@}
3202 //! \name MANIPULATORS
3203 //@{
3205 Integer& operator=(const Integer& t);
3208 Integer& operator+=(const Integer& t);
3210 Integer& operator-=(const Integer& t);
3212 Integer& operator*=(const Integer& t) {return *this = Times(t);}
3214 Integer& operator/=(const Integer& t) {return *this = DividedBy(t);}
3216 Integer& operator%=(const Integer& t) {return *this = Modulo(t);}
3218 Integer& operator/=(word t) {return *this = DividedBy(t);}
3220 Integer& operator%=(word t) {return *this = Modulo(t);}
3223 Integer& operator<<=(unsigned int);
3225 Integer& operator>>=(unsigned int);
3228 void Randomize(RandomNumberGenerator &rng, unsigned int bitcount);
3230 void Randomize(RandomNumberGenerator &rng, const Integer &min, const Integer &max);
3231 //! set this Integer to a random element of {x | min <= x <= max and x is of rnType and x % mod == equiv}
3232 /*! returns false if the set is empty */
3233 bool Randomize(RandomNumberGenerator &rng, const Integer &min, const Integer &max, RandomNumberType rnType, const Integer &equiv=Zero(), const Integer &mod=One());
3235 bool GenerateRandomNoThrow(RandomNumberGenerator &rng, const NameValuePairs &params = g_nullNameValuePairs);
3236 void GenerateRandom(RandomNumberGenerator &rng, const NameValuePairs &params = g_nullNameValuePairs)
3238 if (!GenerateRandomNoThrow(rng, params))
3239 throw RandomNumberNotFound();
3242 //! set the n-th bit to value
3243 void SetBit(unsigned int n, bool value=1);
3244 //! set the n-th byte to value
3245 void SetByte(unsigned int n, byte value);
3248 void Negate();
3250 void SetPositive() {sign = POSITIVE;}
3252 void SetNegative() {if (!!(*this)) sign = NEGATIVE;}
3255 void swap(Integer &a);
3256 //@}
3258 //! \name UNARY OPERATORS
3259 //@{
3261 bool operator!() const;
3263 Integer operator+() const {return *this;}
3265 Integer operator-() const;
3267 Integer& operator++();
3269 Integer& operator--();
3271 Integer operator++(int) {Integer temp = *this; ++*this; return temp;}
3273 Integer operator--(int) {Integer temp = *this; --*this; return temp;}
3274 //@}
3276 //! \name BINARY OPERATORS
3277 //@{
3278 //! signed comparison
3279 /*! \retval -1 if *this < a
3280 \retval 0 if *this = a
3281 \retval 1 if *this > a
3283 int Compare(const Integer& a) const;
3286 Integer Plus(const Integer &b) const;
3288 Integer Minus(const Integer &b) const;
3290 Integer Times(const Integer &b) const;
3292 Integer DividedBy(const Integer &b) const;
3294 Integer Modulo(const Integer &b) const;
3296 Integer DividedBy(word b) const;
3298 word Modulo(word b) const;
3301 Integer operator>>(unsigned int n) const {return Integer(*this)>>=n;}
3303 Integer operator<<(unsigned int n) const {return Integer(*this)<<=n;}
3304 //@}
3306 //! \name OTHER ARITHMETIC FUNCTIONS
3307 //@{
3309 Integer AbsoluteValue() const;
3311 Integer Doubled() const {return Plus(*this);}
3313 Integer Squared() const {return Times(*this);}
3314 //! extract square root, if negative return 0, else return floor of square root
3315 Integer SquareRoot() const;
3316 //! return whether this integer is a perfect square
3317 bool IsSquare() const;
3319 //! is 1 or -1
3320 bool IsUnit() const;
3321 //! return inverse if 1 or -1, otherwise return 0
3322 Integer MultiplicativeInverse() const;
3324 //! modular multiplication
3325 CRYPTOPP_DLL friend Integer a_times_b_mod_c(const Integer &x, const Integer& y, const Integer& m);
3326 //! modular exponentiation
3327 CRYPTOPP_DLL friend Integer a_exp_b_mod_c(const Integer &x, const Integer& e, const Integer& m);
3329 //! calculate r and q such that (a == d*q + r) && (0 <= r < abs(d))
3330 static void Divide(Integer &r, Integer &q, const Integer &a, const Integer &d);
3331 //! use a faster division algorithm when divisor is short
3332 static void Divide(word &r, Integer &q, const Integer &a, word d);
3334 //! returns same result as Divide(r, q, a, Power2(n)), but faster
3335 static void DivideByPowerOf2(Integer &r, Integer &q, const Integer &a, unsigned int n);
3337 //! greatest common divisor
3338 static Integer Gcd(const Integer &a, const Integer &n);
3339 //! calculate multiplicative inverse of *this mod n
3340 Integer InverseMod(const Integer &n) const;
3342 word InverseMod(word n) const;
3343 //@}
3345 //! \name INPUT/OUTPUT
3346 //@{
3348 friend CRYPTOPP_DLL std::istream& operator>>(std::istream& in, Integer &a);
3350 friend CRYPTOPP_DLL std::ostream& operator<<(std::ostream& out, const Integer &a);
3351 //@}
3353 private:
3354 friend class ModularArithmetic;
3355 friend class MontgomeryRepresentation;
3356 friend class HalfMontgomeryRepresentation;
3358 Integer(word value, unsigned int length);
3360 int PositiveCompare(const Integer &t) const;
3361 friend void PositiveAdd(Integer &sum, const Integer &a, const Integer &b);
3362 friend void PositiveSubtract(Integer &diff, const Integer &a, const Integer &b);
3363 friend void PositiveMultiply(Integer &product, const Integer &a, const Integer &b);
3364 friend void PositiveDivide(Integer &remainder, Integer &quotient, const Integer &dividend, const Integer &divisor);
3366 SecAlignedWordBlock reg;
3367 Sign sign;
3371 inline bool operator==(const CryptoPP::Integer& a, const CryptoPP::Integer& b) {return a.Compare(b)==0;}
3373 inline bool operator!=(const CryptoPP::Integer& a, const CryptoPP::Integer& b) {return a.Compare(b)!=0;}
3375 inline bool operator> (const CryptoPP::Integer& a, const CryptoPP::Integer& b) {return a.Compare(b)> 0;}
3377 inline bool operator>=(const CryptoPP::Integer& a, const CryptoPP::Integer& b) {return a.Compare(b)>=0;}
3379 inline bool operator< (const CryptoPP::Integer& a, const CryptoPP::Integer& b) {return a.Compare(b)< 0;}
3381 inline bool operator<=(const CryptoPP::Integer& a, const CryptoPP::Integer& b) {return a.Compare(b)<=0;}
3383 inline CryptoPP::Integer operator+(const CryptoPP::Integer &a, const CryptoPP::Integer &b) {return a.Plus(b);}
3385 inline CryptoPP::Integer operator-(const CryptoPP::Integer &a, const CryptoPP::Integer &b) {return a.Minus(b);}
3387 inline CryptoPP::Integer operator*(const CryptoPP::Integer &a, const CryptoPP::Integer &b) {return a.Times(b);}
3389 inline CryptoPP::Integer operator/(const CryptoPP::Integer &a, const CryptoPP::Integer &b) {return a.DividedBy(b);}
3391 inline CryptoPP::Integer operator%(const CryptoPP::Integer &a, const CryptoPP::Integer &b) {return a.Modulo(b);}
3393 inline CryptoPP::Integer operator/(const CryptoPP::Integer &a, CryptoPP::word b) {return a.DividedBy(b);}
3395 inline CryptoPP::word operator%(const CryptoPP::Integer &a, CryptoPP::word b) {return a.Modulo(b);}
3397 NAMESPACE_END
3399 NAMESPACE_BEGIN(std)
3400 template<> inline void swap(CryptoPP::Integer &a, CryptoPP::Integer &b)
3402 a.swap(b);
3404 NAMESPACE_END
3406 #endif
3407 ////////////////////////////////////////////////////////////////////////////////
3410 ////////////////////////////////////////////////////////////////////////////////
3411 #ifndef CRYPTOPP_ALGEBRA_H
3412 #define CRYPTOPP_ALGEBRA_H
3414 //- #include "config.h"
3416 NAMESPACE_BEGIN(CryptoPP)
3418 class Integer;
3420 // "const Element&" returned by member functions are references
3421 // to internal data members. Since each object may have only
3422 // one such data member for holding results, the following code
3423 // will produce incorrect results:
3424 // abcd = group.Add(group.Add(a,b), group.Add(c,d));
3425 // But this should be fine:
3426 // abcd = group.Add(a, group.Add(b, group.Add(c,d));
3428 //! Abstract Group
3429 template <class T> class CRYPTOPP_NO_VTABLE AbstractGroup
3431 public:
3432 typedef T Element;
3434 virtual ~AbstractGroup() {}
3436 virtual bool Equal(const Element &a, const Element &b) const =0;
3437 virtual const Element& Identity() const =0;
3438 virtual const Element& Add(const Element &a, const Element &b) const =0;
3439 virtual const Element& Inverse(const Element &a) const =0;
3440 virtual bool InversionIsFast() const {return false;}
3442 virtual const Element& Double(const Element &a) const;
3443 virtual const Element& Subtract(const Element &a, const Element &b) const;
3444 virtual Element& Accumulate(Element &a, const Element &b) const;
3445 virtual Element& Reduce(Element &a, const Element &b) const;
3447 virtual Element ScalarMultiply(const Element &a, const Integer &e) const;
3448 virtual Element CascadeScalarMultiply(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const;
3450 virtual void SimultaneousMultiply(Element *results, const Element &base, const Integer *exponents, unsigned int exponentsCount) const;
3453 //! Abstract Ring
3454 template <class T> class CRYPTOPP_NO_VTABLE AbstractRing : public AbstractGroup<T>
3456 public:
3457 typedef T Element;
3459 AbstractRing() {m_mg.m_pRing = this;}
3460 AbstractRing(const AbstractRing &source) {m_mg.m_pRing = this;}
3461 AbstractRing& operator=(const AbstractRing &source) {return *this;}
3463 virtual bool IsUnit(const Element &a) const =0;
3464 virtual const Element& MultiplicativeIdentity() const =0;
3465 virtual const Element& Multiply(const Element &a, const Element &b) const =0;
3466 virtual const Element& MultiplicativeInverse(const Element &a) const =0;
3468 virtual const Element& Square(const Element &a) const;
3469 virtual const Element& Divide(const Element &a, const Element &b) const;
3471 virtual Element Exponentiate(const Element &a, const Integer &e) const;
3472 virtual Element CascadeExponentiate(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const;
3474 virtual void SimultaneousExponentiate(Element *results, const Element &base, const Integer *exponents, unsigned int exponentsCount) const;
3476 virtual const AbstractGroup<T>& MultiplicativeGroup() const
3477 {return m_mg;}
3479 private:
3480 class MultiplicativeGroupT : public AbstractGroup<T>
3482 public:
3483 const AbstractRing<T>& GetRing() const
3484 {return *m_pRing;}
3486 bool Equal(const Element &a, const Element &b) const
3487 {return GetRing().Equal(a, b);}
3489 const Element& Identity() const
3490 {return GetRing().MultiplicativeIdentity();}
3492 const Element& Add(const Element &a, const Element &b) const
3493 {return GetRing().Multiply(a, b);}
3495 Element& Accumulate(Element &a, const Element &b) const
3496 {return a = GetRing().Multiply(a, b);}
3498 const Element& Inverse(const Element &a) const
3499 {return GetRing().MultiplicativeInverse(a);}
3501 const Element& Subtract(const Element &a, const Element &b) const
3502 {return GetRing().Divide(a, b);}
3504 Element& Reduce(Element &a, const Element &b) const
3505 {return a = GetRing().Divide(a, b);}
3507 const Element& Double(const Element &a) const
3508 {return GetRing().Square(a);}
3510 Element ScalarMultiply(const Element &a, const Integer &e) const
3511 {return GetRing().Exponentiate(a, e);}
3513 Element CascadeScalarMultiply(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const
3514 {return GetRing().CascadeExponentiate(x, e1, y, e2);}
3516 void SimultaneousMultiply(Element *results, const Element &base, const Integer *exponents, unsigned int exponentsCount) const
3517 {GetRing().SimultaneousExponentiate(results, base, exponents, exponentsCount);}
3519 const AbstractRing<T> *m_pRing;
3522 MultiplicativeGroupT m_mg;
3525 // ********************************************************
3527 //! Abstract Euclidean Domain
3528 template <class T> class CRYPTOPP_NO_VTABLE AbstractEuclideanDomain : public AbstractRing<T>
3530 public:
3531 typedef T Element;
3533 virtual void DivisionAlgorithm(Element &r, Element &q, const Element &a, const Element &d) const =0;
3535 virtual const Element& Mod(const Element &a, const Element &b) const =0;
3536 virtual const Element& Gcd(const Element &a, const Element &b) const;
3538 protected:
3539 mutable Element result;
3542 // ********************************************************
3544 //! EuclideanDomainOf
3545 template <class T> class EuclideanDomainOf : public AbstractEuclideanDomain<T>
3547 public:
3548 typedef T Element;
3550 EuclideanDomainOf() {}
3552 bool Equal(const Element &a, const Element &b) const
3553 {return a==b;}
3555 const Element& Identity() const
3556 {return Element::Zero();}
3558 const Element& Add(const Element &a, const Element &b) const
3559 {return result = a+b;}
3561 Element& Accumulate(Element &a, const Element &b) const
3562 {return a+=b;}
3564 const Element& Inverse(const Element &a) const
3565 {return result = -a;}
3567 const Element& Subtract(const Element &a, const Element &b) const
3568 {return result = a-b;}
3570 Element& Reduce(Element &a, const Element &b) const
3571 {return a-=b;}
3573 const Element& Double(const Element &a) const
3574 {return result = a.Doubled();}
3576 const Element& MultiplicativeIdentity() const
3577 {return Element::One();}
3579 const Element& Multiply(const Element &a, const Element &b) const
3580 {return result = a*b;}
3582 const Element& Square(const Element &a) const
3583 {return result = a.Squared();}
3585 bool IsUnit(const Element &a) const
3586 {return a.IsUnit();}
3588 const Element& MultiplicativeInverse(const Element &a) const
3589 {return result = a.MultiplicativeInverse();}
3591 const Element& Divide(const Element &a, const Element &b) const
3592 {return result = a/b;}
3594 const Element& Mod(const Element &a, const Element &b) const
3595 {return result = a%b;}
3597 void DivisionAlgorithm(Element &r, Element &q, const Element &a, const Element &d) const
3598 {Element::Divide(r, q, a, d);}
3600 bool operator==(const EuclideanDomainOf<T> &rhs) const
3601 {return true;}
3603 private:
3604 mutable Element result;
3607 NAMESPACE_END
3609 #endif
3610 ////////////////////////////////////////////////////////////////////////////////
3613 ////////////////////////////////////////////////////////////////////////////////
3614 #ifndef CRYPTOPP_MODARITH_H
3615 #define CRYPTOPP_MODARITH_H
3617 // implementations are in integer.cpp
3619 //- #include "cryptlib.h"
3620 //- #include "misc.h"
3621 //- #include "integer.h"
3622 //- #include "algebra.h"
3624 NAMESPACE_BEGIN(CryptoPP)
3626 //! ring of congruence classes modulo n
3627 /*! \note this implementation represents each congruence class as the smallest non-negative integer in that class */
3628 class CRYPTOPP_DLL ModularArithmetic : public AbstractRing<Integer>
3630 public:
3632 typedef int RandomizationParameter;
3633 typedef Integer Element;
3635 ModularArithmetic(const Integer &mod = Integer::One())
3636 : AbstractRing<Integer>(),
3637 modulus(mod), result((word)0, modulus.reg.size()) {}
3639 ModularArithmetic(const ModularArithmetic &ma)
3640 : AbstractRing<Integer>(),
3641 modulus(ma.modulus), result((word)0, modulus.reg.size()) {}
3643 ModularArithmetic(BufferedTransformation &bt); // construct from BER encoded parameters
3645 virtual ModularArithmetic * Clone() const {return new ModularArithmetic(*this);}
3647 void DEREncode(BufferedTransformation &bt) const;
3649 void DEREncodeElement(BufferedTransformation &out, const Element &a) const;
3650 void BERDecodeElement(BufferedTransformation &in, Element &a) const;
3652 const Integer& GetModulus() const {return modulus;}
3653 void SetModulus(const Integer &newModulus) {modulus = newModulus; result.reg.resize(modulus.reg.size());}
3655 virtual bool IsMontgomeryRepresentation() const {return false;}
3657 virtual Integer ConvertIn(const Integer &a) const
3658 {return a%modulus;}
3660 virtual Integer ConvertOut(const Integer &a) const
3661 {return a;}
3663 const Integer& Half(const Integer &a) const;
3665 bool Equal(const Integer &a, const Integer &b) const
3666 {return a==b;}
3668 const Integer& Identity() const
3669 {return Integer::Zero();}
3671 const Integer& Add(const Integer &a, const Integer &b) const;
3673 Integer& Accumulate(Integer &a, const Integer &b) const;
3675 const Integer& Inverse(const Integer &a) const;
3677 const Integer& Subtract(const Integer &a, const Integer &b) const;
3679 Integer& Reduce(Integer &a, const Integer &b) const;
3681 const Integer& Double(const Integer &a) const
3682 {return Add(a, a);}
3684 const Integer& MultiplicativeIdentity() const
3685 {return Integer::One();}
3687 const Integer& Multiply(const Integer &a, const Integer &b) const
3688 {return result1 = a*b%modulus;}
3690 const Integer& Square(const Integer &a) const
3691 {return result1 = a.Squared()%modulus;}
3693 bool IsUnit(const Integer &a) const
3694 {return Integer::Gcd(a, modulus).IsUnit();}
3696 const Integer& MultiplicativeInverse(const Integer &a) const
3697 {return result1 = a.InverseMod(modulus);}
3699 const Integer& Divide(const Integer &a, const Integer &b) const
3700 {return Multiply(a, MultiplicativeInverse(b));}
3702 Integer CascadeExponentiate(const Integer &x, const Integer &e1, const Integer &y, const Integer &e2) const;
3704 void SimultaneousExponentiate(Element *results, const Element &base, const Integer *exponents, unsigned int exponentsCount) const;
3706 unsigned int MaxElementBitLength() const
3707 {return (modulus-1).BitCount();}
3709 unsigned int MaxElementByteLength() const
3710 {return (modulus-1).ByteCount();}
3712 Element RandomElement( RandomNumberGenerator &rng , const RandomizationParameter& /*ignore_for_now*/ = 0 ) const
3713 // left RandomizationParameter arg as ref in case RandomizationParameter becomes a more complicated struct
3715 return Element( rng , Integer( (long) 0) , modulus - Integer( (long) 1 ) ) ;
3718 bool operator==(const ModularArithmetic &rhs) const
3719 {return modulus == rhs.modulus;}
3721 static const RandomizationParameter DefaultRandomizationParameter ;
3723 protected:
3724 Integer modulus;
3725 mutable Integer result, result1;
3729 // const ModularArithmetic::RandomizationParameter ModularArithmetic::DefaultRandomizationParameter = 0 ;
3731 //! do modular arithmetics in Montgomery representation for increased speed
3732 /*! \note the Montgomery representation represents each congruence class [a] as a*r%n, where r is a convenient power of 2 */
3733 class CRYPTOPP_DLL MontgomeryRepresentation : public ModularArithmetic
3735 public:
3736 MontgomeryRepresentation(const Integer &modulus); // modulus must be odd
3738 virtual ModularArithmetic * Clone() const {return new MontgomeryRepresentation(*this);}
3740 bool IsMontgomeryRepresentation() const {return true;}
3742 Integer ConvertIn(const Integer &a) const
3743 {return (a<<(WORD_BITS*modulus.reg.size()))%modulus;}
3745 Integer ConvertOut(const Integer &a) const;
3747 const Integer& MultiplicativeIdentity() const
3748 {return result1 = Integer::Power2(WORD_BITS*modulus.reg.size())%modulus;}
3750 const Integer& Multiply(const Integer &a, const Integer &b) const;
3752 const Integer& Square(const Integer &a) const;
3754 const Integer& MultiplicativeInverse(const Integer &a) const;
3756 Integer CascadeExponentiate(const Integer &x, const Integer &e1, const Integer &y, const Integer &e2) const
3757 {return AbstractRing<Integer>::CascadeExponentiate(x, e1, y, e2);}
3759 void SimultaneousExponentiate(Element *results, const Element &base, const Integer *exponents, unsigned int exponentsCount) const
3760 {AbstractRing<Integer>::SimultaneousExponentiate(results, base, exponents, exponentsCount);}
3762 private:
3763 Integer u;
3764 mutable SecAlignedWordBlock workspace;
3767 NAMESPACE_END
3769 #endif
3770 ////////////////////////////////////////////////////////////////////////////////
3773 ////////////////////////////////////////////////////////////////////////////////
3774 // simple.h - written and placed in the public domain by Wei Dai
3775 /*! \file
3776 Simple non-interface classes derived from classes in cryptlib.h.
3779 #ifndef CRYPTOPP_SIMPLE_H
3780 #define CRYPTOPP_SIMPLE_H
3782 //- #include "cryptlib.h"
3783 //- #include "misc.h"
3785 NAMESPACE_BEGIN(CryptoPP)
3787 //! _
3788 template <class DERIVED, class BASE>
3789 class CRYPTOPP_NO_VTABLE ClonableImpl : public BASE
3791 public:
3792 Clonable * Clone() const {return new DERIVED(*static_cast<const DERIVED *>(this));}
3795 //! _
3796 template <class BASE, class ALGORITHM_INFO=BASE>
3797 class CRYPTOPP_NO_VTABLE AlgorithmImpl : public BASE
3799 public:
3800 static std::string StaticAlgorithmName() {return ALGORITHM_INFO::StaticAlgorithmName();}
3801 std::string AlgorithmName() const {return ALGORITHM_INFO::StaticAlgorithmName();}
3804 //! _
3805 class CRYPTOPP_DLL InvalidKeyLength : public InvalidArgument
3807 public:
3808 explicit InvalidKeyLength(const std::string &algorithm, unsigned int length) : InvalidArgument(algorithm + ": " + IntToString(length, 10) + " is not a valid key length") {}
3811 //! _
3812 // TODO: look into this virtual inheritance
3813 class CRYPTOPP_DLL ASN1CryptoMaterial : virtual public ASN1Object, virtual public CryptoMaterial
3815 public:
3816 void Save(BufferedTransformation &bt) const
3817 {BEREncode(bt);}
3818 void Load(BufferedTransformation &bt)
3819 {BERDecode(bt);}
3822 // *****************************
3824 //! _
3825 template <class T>
3826 class CRYPTOPP_NO_VTABLE Bufferless : public T
3828 public:
3829 bool IsolatedFlush(bool /* hardFlush */, bool /* blocking */) {return false;}
3832 //! _
3833 template <class T>
3834 class CRYPTOPP_NO_VTABLE Unflushable : public T
3836 public:
3837 bool Flush(bool completeFlush, int propagation=-1, bool blocking=true)
3838 {return ChannelFlush(this->NULL_CHANNEL, completeFlush, propagation, blocking);}
3839 bool IsolatedFlush(bool /* hardFlush */, bool /* blocking */)
3840 {assert(false); return false;}
3841 bool ChannelFlush(const std::string &channel, bool hardFlush, int propagation=-1, bool blocking=true)
3843 if (hardFlush && !InputBufferIsEmpty())
3844 throw CannotFlush("Unflushable<T>: this object has buffered input that cannot be flushed");
3845 else
3847 BufferedTransformation *attached = this->AttachedTransformation();
3848 return attached && propagation ? attached->ChannelFlush(channel, hardFlush, propagation-1, blocking) : false;
3852 protected:
3853 virtual bool InputBufferIsEmpty() const {return false;}
3856 //! _
3857 template <class T>
3858 class CRYPTOPP_NO_VTABLE InputRejecting : public T
3860 public:
3861 struct InputRejected : public NotImplemented
3862 {InputRejected() : NotImplemented("BufferedTransformation: this object doesn't allow input") {}};
3864 // shouldn't be calling these functions on this class
3865 unsigned int Put2(const byte* /* begin */, unsigned int /* length */, int /* messageEnd */, bool /* blocking */)
3866 {throw InputRejected();}
3867 bool IsolatedFlush(bool, bool) {return false;}
3868 bool IsolatedMessageSeriesEnd(bool) {throw InputRejected();}
3870 unsigned int ChannelPut2(const std::string& /* channel */, const byte* /* begin */, unsigned int /* length */, int /* messageEnd */, bool /* blocking */)
3871 {throw InputRejected();}
3872 bool ChannelMessageSeriesEnd(const std::string &, int, bool) {throw InputRejected();}
3875 //! _
3876 template <class T>
3877 class CRYPTOPP_NO_VTABLE CustomFlushPropagation : public T
3879 public:
3880 virtual bool Flush(bool hardFlush, int propagation=-1, bool blocking=true) =0;
3882 private:
3883 bool IsolatedFlush(bool /* hardFlush */, bool /* blocking */) {assert(false); return false;}
3886 //! _
3887 template <class T>
3888 class CRYPTOPP_NO_VTABLE CustomSignalPropagation : public CustomFlushPropagation<T>
3890 public:
3891 virtual void Initialize(const NameValuePairs &parameters=g_nullNameValuePairs, int propagation=-1) =0;
3893 private:
3894 void IsolatedInitialize(const NameValuePairs& /* parameters */) {assert(false);}
3897 //! _
3898 template <class T>
3899 class CRYPTOPP_NO_VTABLE AutoSignaling : public T
3901 public:
3902 AutoSignaling(int propagation=-1) : m_autoSignalPropagation(propagation) {}
3904 void SetAutoSignalPropagation(int propagation)
3905 {m_autoSignalPropagation = propagation;}
3906 int GetAutoSignalPropagation() const
3907 {return m_autoSignalPropagation;}
3909 private:
3910 int m_autoSignalPropagation;
3913 //! A BufferedTransformation that only contains pre-existing data as "output"
3914 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Store : public AutoSignaling<InputRejecting<BufferedTransformation> >
3916 public:
3917 Store() : m_messageEnd(false) {}
3919 void IsolatedInitialize(const NameValuePairs &parameters)
3921 m_messageEnd = false;
3922 StoreInitialize(parameters);
3925 unsigned int NumberOfMessages() const {return m_messageEnd ? 0 : 1;}
3926 bool GetNextMessage();
3927 unsigned int CopyMessagesTo(BufferedTransformation &target, unsigned int count=UINT_MAX, const std::string &channel=NULL_CHANNEL) const;
3929 protected:
3930 virtual void StoreInitialize(const NameValuePairs &parameters) =0;
3932 bool m_messageEnd;
3935 //! A BufferedTransformation that doesn't produce any retrievable output
3936 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Sink : public BufferedTransformation
3938 protected:
3939 // make these functions protected to help prevent unintentional calls to them
3940 BufferedTransformation::Get;
3941 BufferedTransformation::Peek;
3942 BufferedTransformation::TransferTo;
3943 BufferedTransformation::CopyTo;
3944 BufferedTransformation::CopyRangeTo;
3945 BufferedTransformation::TransferMessagesTo;
3946 BufferedTransformation::CopyMessagesTo;
3947 BufferedTransformation::TransferAllTo;
3948 BufferedTransformation::CopyAllTo;
3949 unsigned int TransferTo2(BufferedTransformation& /* target */, unsigned long &transferBytes, const std::string& /* channel */ = NULL_CHANNEL, bool /* blocking */ = true)
3950 {transferBytes = 0; return 0;}
3951 unsigned int CopyRangeTo2(BufferedTransformation& /* target */, unsigned long& /* begin */, unsigned long /* end */ = ULONG_MAX, const std::string& /* channel */ = NULL_CHANNEL, bool /* blocking */ = true) const
3952 {return 0;}
3955 class CRYPTOPP_DLL BitBucket : public Bufferless<Sink>
3957 public:
3958 std::string AlgorithmName() const {return "BitBucket";}
3959 void IsolatedInitialize(const NameValuePairs& /* parameters */) {}
3960 unsigned int Put2(const byte* /* begin */, unsigned int /* length */, int /* messageEnd */, bool /* blocking */)
3961 {return 0;}
3964 NAMESPACE_END
3966 #endif
3967 ////////////////////////////////////////////////////////////////////////////////
3970 ////////////////////////////////////////////////////////////////////////////////
3971 // specification file for an unlimited queue for storing bytes
3973 #ifndef CRYPTOPP_QUEUE_H
3974 #define CRYPTOPP_QUEUE_H
3976 //- #include "simple.h"
3977 //#include <algorithm>
3979 NAMESPACE_BEGIN(CryptoPP)
3981 /** The queue is implemented as a linked list of byte arrays, but you don't need to
3982 know about that. So just ignore this next line. :) */
3983 class ByteQueueNode;
3985 //! Byte Queue
3986 class CRYPTOPP_DLL ByteQueue : public Bufferless<BufferedTransformation>
3988 public:
3989 ByteQueue(unsigned int nodeSize=0);
3990 ByteQueue(const ByteQueue &copy);
3991 ~ByteQueue();
3993 unsigned long MaxRetrievable() const
3994 {return CurrentSize();}
3995 bool AnyRetrievable() const
3996 {return !IsEmpty();}
3998 void IsolatedInitialize(const NameValuePairs &parameters);
3999 byte * CreatePutSpace(unsigned int &size);
4000 unsigned int Put2(const byte *inString, unsigned int length, int messageEnd, bool blocking);
4002 unsigned int Get(byte &outByte);
4003 unsigned int Get(byte *outString, unsigned int getMax);
4005 unsigned int Peek(byte &outByte) const;
4006 unsigned int Peek(byte *outString, unsigned int peekMax) const;
4008 unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
4009 unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const;
4011 // these member functions are not inherited
4012 void SetNodeSize(unsigned int nodeSize);
4014 unsigned long CurrentSize() const;
4015 bool IsEmpty() const;
4017 void Clear();
4019 void Unget(byte inByte);
4020 void Unget(const byte *inString, unsigned int length);
4022 const byte * Spy(unsigned int &contiguousSize) const;
4024 void LazyPut(const byte *inString, unsigned int size);
4025 void LazyPutModifiable(byte *inString, unsigned int size);
4026 void UndoLazyPut(unsigned int size);
4027 void FinalizeLazyPut();
4029 ByteQueue & operator=(const ByteQueue &rhs);
4030 bool operator==(const ByteQueue &rhs) const;
4031 byte operator[](unsigned long i) const;
4032 void swap(ByteQueue &rhs);
4034 class Walker : public InputRejecting<BufferedTransformation>
4036 public:
4037 Walker(const ByteQueue &queue)
4038 : m_queue(queue) {Initialize();}
4040 unsigned long GetCurrentPosition() {return m_position;}
4042 unsigned long MaxRetrievable() const
4043 {return m_queue.CurrentSize() - m_position;}
4045 void IsolatedInitialize(const NameValuePairs &parameters);
4047 unsigned int Get(byte &outByte);
4048 unsigned int Get(byte *outString, unsigned int getMax);
4050 unsigned int Peek(byte &outByte) const;
4051 unsigned int Peek(byte *outString, unsigned int peekMax) const;
4053 unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
4054 unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const;
4056 private:
4057 const ByteQueue &m_queue;
4058 const ByteQueueNode *m_node;
4059 unsigned long m_position;
4060 unsigned int m_offset;
4061 const byte *m_lazyString;
4062 unsigned int m_lazyLength;
4065 friend class Walker;
4067 private:
4068 void CleanupUsedNodes();
4069 void CopyFrom(const ByteQueue &copy);
4070 void Destroy();
4072 bool m_autoNodeSize;
4073 unsigned int m_nodeSize;
4074 ByteQueueNode *m_head, *m_tail;
4075 byte *m_lazyString;
4076 unsigned int m_lazyLength;
4077 bool m_lazyStringModifiable;
4080 NAMESPACE_END
4082 NAMESPACE_BEGIN(std)
4083 template<> inline void swap(CryptoPP::ByteQueue &a, CryptoPP::ByteQueue &b)
4085 a.swap(b);
4087 NAMESPACE_END
4089 #endif
4090 ////////////////////////////////////////////////////////////////////////////////
4093 ////////////////////////////////////////////////////////////////////////////////
4094 #ifndef CRYPTOPP_ALGPARAM_H
4095 #define CRYPTOPP_ALGPARAM_H
4097 //- #include "cryptlib.h"
4098 //- #include "smartptr.h"
4099 //- #include "secblock.h"
4101 NAMESPACE_BEGIN(CryptoPP)
4103 //! used to pass byte array input as part of a NameValuePairs object
4104 /*! the deepCopy option is used when the NameValuePairs object can't
4105 keep a copy of the data available */
4106 class ConstByteArrayParameter
4108 public:
4109 ConstByteArrayParameter(const char *data = NULL, bool deepCopy = false)
4111 Assign((const byte *)data, data ? strlen(data) : 0, deepCopy);
4113 ConstByteArrayParameter(const byte *data, unsigned int datasize, bool deepCopy = false)
4115 Assign(data, datasize, deepCopy);
4117 template <class T> ConstByteArrayParameter(const T &string, bool deepCopy = false)
4119 CRYPTOPP_COMPILE_ASSERT(sizeof(CPP_TYPENAME T::value_type) == 1);
4120 Assign((const byte *)string.data(), string.size(), deepCopy);
4123 void Assign(const byte *data, unsigned int datasize, bool deepCopy)
4125 if (deepCopy)
4126 m_block.Assign(data, datasize);
4127 else
4129 m_data = data;
4130 m_size = datasize;
4132 m_deepCopy = deepCopy;
4135 const byte *begin() const {return m_deepCopy ? m_block.begin() : m_data;}
4136 const byte *end() const {return m_deepCopy ? m_block.end() : m_data + m_size;}
4137 unsigned int size() const {return m_deepCopy ? m_block.size() : m_size;}
4139 private:
4140 bool m_deepCopy;
4141 const byte *m_data;
4142 unsigned int m_size;
4143 SecByteBlock m_block;
4146 class ByteArrayParameter
4148 public:
4149 ByteArrayParameter(byte *data = NULL, unsigned int datasize = 0)
4150 : m_data(data), m_size(datasize) {}
4151 ByteArrayParameter(SecByteBlock &block)
4152 : m_data(block.begin()), m_size(block.size()) {}
4154 byte *begin() const {return m_data;}
4155 byte *end() const {return m_data + m_size;}
4156 unsigned int size() const {return m_size;}
4158 private:
4159 byte *m_data;
4160 unsigned int m_size;
4163 class CRYPTOPP_DLL CombinedNameValuePairs : public NameValuePairs
4165 public:
4166 CombinedNameValuePairs(const NameValuePairs &pairs1, const NameValuePairs &pairs2)
4167 : m_pairs1(pairs1), m_pairs2(pairs2) {}
4169 bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const;
4171 private:
4172 const NameValuePairs &m_pairs1, &m_pairs2;
4175 template <class T, class BASE>
4176 class GetValueHelperClass
4178 public:
4179 GetValueHelperClass(const T *pObject, const char *name, const std::type_info &valueType, void *pValue, const NameValuePairs *searchFirst)
4180 : m_pObject(pObject), m_name(name), m_valueType(&valueType), m_pValue(pValue), m_found(false), m_getValueNames(false)
4182 if (strcmp(m_name, "ValueNames") == 0)
4184 m_found = m_getValueNames = true;
4185 NameValuePairs::ThrowIfTypeMismatch(m_name, typeid(std::string), *m_valueType);
4186 if (searchFirst)
4187 searchFirst->GetVoidValue(m_name, valueType, pValue);
4188 if (typeid(T) != typeid(BASE))
4189 pObject->BASE::GetVoidValue(m_name, valueType, pValue);
4190 ((*reinterpret_cast<std::string *>(m_pValue) += "ThisPointer:") += typeid(T).name()) += ';';
4193 if (!m_found && strncmp(m_name, "ThisPointer:", 12) == 0 && strcmp(m_name+12, typeid(T).name()) == 0)
4195 NameValuePairs::ThrowIfTypeMismatch(m_name, typeid(T *), *m_valueType);
4196 *reinterpret_cast<const T **>(pValue) = pObject;
4197 m_found = true;
4198 return;
4201 if (!m_found && searchFirst)
4202 m_found = searchFirst->GetVoidValue(m_name, valueType, pValue);
4204 if (!m_found && typeid(T) != typeid(BASE))
4205 m_found = pObject->BASE::GetVoidValue(m_name, valueType, pValue);
4208 operator bool() const {return m_found;}
4210 template <class R>
4211 GetValueHelperClass<T,BASE> & operator()(const char *name, const R & (T::*pm)() const)
4213 if (m_getValueNames)
4214 (*reinterpret_cast<std::string *>(m_pValue) += name) += ";";
4215 if (!m_found && strcmp(name, m_name) == 0)
4217 NameValuePairs::ThrowIfTypeMismatch(name, typeid(R), *m_valueType);
4218 *reinterpret_cast<R *>(m_pValue) = (m_pObject->*pm)();
4219 m_found = true;
4221 return *this;
4224 GetValueHelperClass<T,BASE> &Assignable()
4226 if (m_getValueNames)
4227 ((*reinterpret_cast<std::string *>(m_pValue) += "ThisObject:") += typeid(T).name()) += ';';
4228 if (!m_found && strncmp(m_name, "ThisObject:", 11) == 0 && strcmp(m_name+11, typeid(T).name()) == 0)
4230 NameValuePairs::ThrowIfTypeMismatch(m_name, typeid(T), *m_valueType);
4231 *reinterpret_cast<T *>(m_pValue) = *m_pObject;
4232 m_found = true;
4234 return *this;
4237 private:
4238 const T *m_pObject;
4239 const char *m_name;
4240 const std::type_info *m_valueType;
4241 void *m_pValue;
4242 bool m_found, m_getValueNames;
4245 template <class BASE, class T>
4246 GetValueHelperClass<T, BASE> GetValueHelper(const T *pObject, const char *name, const std::type_info &valueType, void *pValue, const NameValuePairs *searchFirst=NULL, BASE* /* dummy */ = NULL)
4248 return GetValueHelperClass<T, BASE>(pObject, name, valueType, pValue, searchFirst);
4251 template <class T>
4252 GetValueHelperClass<T, T> GetValueHelper(const T *pObject, const char *name, const std::type_info &valueType, void *pValue, const NameValuePairs *searchFirst=NULL)
4254 return GetValueHelperClass<T, T>(pObject, name, valueType, pValue, searchFirst);
4257 // ********************************************************
4259 template <class R>
4260 R Hack_DefaultValueFromConstReferenceType(const R &)
4262 return R();
4265 template <class R>
4266 bool Hack_GetValueIntoConstReference(const NameValuePairs &source, const char *name, const R &value)
4268 return source.GetValue(name, const_cast<R &>(value));
4271 template <class T, class BASE>
4272 class AssignFromHelperClass
4274 public:
4275 AssignFromHelperClass(T *pObject, const NameValuePairs &source)
4276 : m_pObject(pObject), m_source(source), m_done(false)
4278 if (source.GetThisObject(*pObject))
4279 m_done = true;
4280 else if (typeid(BASE) != typeid(T))
4281 pObject->BASE::AssignFrom(source);
4284 template <class R>
4285 AssignFromHelperClass & operator()(const char *name, void (T::*pm)(R)) // VC60 workaround: "const R &" here causes compiler error
4287 if (!m_done)
4289 R value = Hack_DefaultValueFromConstReferenceType(reinterpret_cast<R>(*(int *)NULL));
4290 if (!Hack_GetValueIntoConstReference(m_source, name, value))
4291 throw InvalidArgument(std::string(typeid(T).name()) + ": Missing required parameter '" + name + "'");
4292 (m_pObject->*pm)(value);
4294 return *this;
4297 template <class R, class S>
4298 AssignFromHelperClass & operator()(const char *name1, const char *name2, void (T::*pm)(R, S)) // VC60 workaround: "const R &" here causes compiler error
4300 if (!m_done)
4302 R value1 = Hack_DefaultValueFromConstReferenceType(reinterpret_cast<R>(*(int *)NULL));
4303 if (!Hack_GetValueIntoConstReference(m_source, name1, value1))
4304 throw InvalidArgument(std::string(typeid(T).name()) + ": Missing required parameter '" + name1 + "'");
4305 S value2 = Hack_DefaultValueFromConstReferenceType(reinterpret_cast<S>(*(int *)NULL));
4306 if (!Hack_GetValueIntoConstReference(m_source, name2, value2))
4307 throw InvalidArgument(std::string(typeid(T).name()) + ": Missing required parameter '" + name2 + "'");
4308 (m_pObject->*pm)(value1, value2);
4310 return *this;
4313 private:
4314 T *m_pObject;
4315 const NameValuePairs &m_source;
4316 bool m_done;
4319 template <class BASE, class T>
4320 AssignFromHelperClass<T, BASE> AssignFromHelper(T *pObject, const NameValuePairs &source, BASE* /* dummy */ = NULL)
4322 return AssignFromHelperClass<T, BASE>(pObject, source);
4325 template <class T>
4326 AssignFromHelperClass<T, T> AssignFromHelper(T *pObject, const NameValuePairs &source)
4328 return AssignFromHelperClass<T, T>(pObject, source);
4331 // ********************************************************
4333 // This should allow the linker to discard Integer code if not needed.
4334 CRYPTOPP_DLL extern bool (*AssignIntToInteger)(const std::type_info &valueType, void *pInteger, const void *pInt);
4336 CRYPTOPP_DLL const std::type_info & IntegerTypeId();
4338 class CRYPTOPP_DLL AlgorithmParametersBase : public NameValuePairs
4340 public:
4341 class ParameterNotUsed : public Exception
4343 public:
4344 ParameterNotUsed(const char *name) : Exception(OTHER_ERROR, std::string("AlgorithmParametersBase: parameter \"") + name + "\" not used") {}
4347 AlgorithmParametersBase(const char *name, bool throwIfNotUsed)
4348 : m_name(name), m_throwIfNotUsed(throwIfNotUsed), m_used(false) {}
4350 ~AlgorithmParametersBase()
4352 #ifdef CRYPTOPP_UNCAUGHT_EXCEPTION_AVAILABLE
4353 if (!std::uncaught_exception())
4354 #else
4356 #endif
4358 if (m_throwIfNotUsed && !m_used)
4359 throw ParameterNotUsed(m_name);
4361 #ifndef CRYPTOPP_UNCAUGHT_EXCEPTION_AVAILABLE
4362 catch(...)
4365 #endif
4368 bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const;
4370 protected:
4371 virtual void AssignValue(const char *name, const std::type_info &valueType, void *pValue) const =0;
4372 virtual const NameValuePairs & GetParent() const =0;
4374 const char *m_name;
4375 bool m_throwIfNotUsed;
4376 mutable bool m_used;
4379 template <class T>
4380 class AlgorithmParametersBase2 : public AlgorithmParametersBase
4382 public:
4383 AlgorithmParametersBase2(const char *name, const T &value, bool throwIfNotUsed) : AlgorithmParametersBase(name, throwIfNotUsed), m_value(value) {}
4385 void AssignValue(const char *name, const std::type_info &valueType, void *pValue) const
4387 // special case for retrieving an Integer parameter when an int was passed in
4388 if (!(AssignIntToInteger != NULL && typeid(T) == typeid(int) && AssignIntToInteger(valueType, pValue, &m_value)))
4390 ThrowIfTypeMismatch(name, typeid(T), valueType);
4391 *reinterpret_cast<T *>(pValue) = m_value;
4395 protected:
4396 T m_value;
4399 template <class PARENT, class T>
4400 class AlgorithmParameters : public AlgorithmParametersBase2<T>
4402 public:
4403 AlgorithmParameters(const PARENT &parent, const char *name, const T &value, bool throwIfNotUsed)
4404 : AlgorithmParametersBase2<T>(name, value, throwIfNotUsed), m_parent(parent)
4407 AlgorithmParameters(const AlgorithmParameters &copy)
4408 : AlgorithmParametersBase2<T>(copy), m_parent(copy.m_parent)
4410 copy.m_used = true;
4413 template <class R>
4414 AlgorithmParameters<AlgorithmParameters<PARENT,T>, R> operator()(const char *name, const R &value) const
4416 return AlgorithmParameters<AlgorithmParameters<PARENT,T>, R>(*this, name, value, this->m_throwIfNotUsed);
4419 template <class R>
4420 AlgorithmParameters<AlgorithmParameters<PARENT,T>, R> operator()(const char *name, const R &value, bool throwIfNotUsed) const
4422 return AlgorithmParameters<AlgorithmParameters<PARENT,T>, R>(*this, name, value, throwIfNotUsed);
4425 private:
4426 const NameValuePairs & GetParent() const {return m_parent;}
4427 PARENT m_parent;
4430 //! Create an object that implements NameValuePairs for passing parameters
4431 /*! \param throwIfNotUsed if true, the object will throw an exception if the value is not accessed
4432 \note throwIfNotUsed is ignored if using a compiler that does not support std::uncaught_exception(),
4433 such as MSVC 7.0 and earlier.
4434 \note A NameValuePairs object containing an arbitrary number of name value pairs may be constructed by
4435 repeatedly using operator() on the object returned by MakeParameters, for example:
4436 const NameValuePairs &parameters = MakeParameters(name1, value1)(name2, value2)(name3, value3);
4438 template <class T>
4439 AlgorithmParameters<NullNameValuePairs,T> MakeParameters(const char *name, const T &value, bool throwIfNotUsed = true)
4441 return AlgorithmParameters<NullNameValuePairs,T>(g_nullNameValuePairs, name, value, throwIfNotUsed);
4444 #define CRYPTOPP_GET_FUNCTION_ENTRY(name) (Name::name(), &ThisClass::Get##name)
4445 #define CRYPTOPP_SET_FUNCTION_ENTRY(name) (Name::name(), &ThisClass::Set##name)
4446 #define CRYPTOPP_SET_FUNCTION_ENTRY2(name1, name2) (Name::name1(), Name::name2(), &ThisClass::Set##name1##And##name2)
4448 NAMESPACE_END
4450 #endif
4451 ////////////////////////////////////////////////////////////////////////////////
4454 ////////////////////////////////////////////////////////////////////////////////
4455 #ifndef CRYPTOPP_FILTERS_H
4456 #define CRYPTOPP_FILTERS_H
4458 //- #include "simple.h"
4459 //- #include "secblock.h"
4460 //- #include "misc.h"
4461 //- #include "smartptr.h"
4462 //- #include "queue.h"
4463 //- #include "algparam.h"
4465 NAMESPACE_BEGIN(CryptoPP)
4467 /// provides an implementation of BufferedTransformation's attachment interface
4468 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Filter : public BufferedTransformation, public NotCopyable
4470 public:
4471 Filter(BufferedTransformation *attachment = NULL);
4473 bool Attachable() {return true;}
4474 BufferedTransformation *AttachedTransformation();
4475 const BufferedTransformation *AttachedTransformation() const;
4476 void Detach(BufferedTransformation *newAttachment = NULL);
4478 unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
4479 unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const;
4481 void Initialize(const NameValuePairs &parameters=g_nullNameValuePairs, int propagation=-1);
4482 bool Flush(bool hardFlush, int propagation=-1, bool blocking=true);
4483 bool MessageSeriesEnd(int propagation=-1, bool blocking=true);
4485 protected:
4486 virtual BufferedTransformation * NewDefaultAttachment() const;
4487 void Insert(Filter *nextFilter); // insert filter after this one
4489 virtual bool ShouldPropagateMessageEnd() const {return true;}
4490 virtual bool ShouldPropagateMessageSeriesEnd() const {return true;}
4492 void PropagateInitialize(const NameValuePairs &parameters, int propagation);
4494 unsigned int Output(int outputSite, const byte *inString, unsigned int length, int messageEnd, bool blocking, const std::string &channel=NULL_CHANNEL);
4495 unsigned int OutputModifiable(int outputSite, byte *inString, unsigned int length, int messageEnd, bool blocking, const std::string &channel=NULL_CHANNEL);
4496 bool OutputMessageEnd(int outputSite, int propagation, bool blocking, const std::string &channel=NULL_CHANNEL);
4497 bool OutputFlush(int outputSite, bool hardFlush, int propagation, bool blocking, const std::string &channel=NULL_CHANNEL);
4498 bool OutputMessageSeriesEnd(int outputSite, int propagation, bool blocking, const std::string &channel=NULL_CHANNEL);
4500 private:
4501 member_ptr<BufferedTransformation> m_attachment;
4503 protected:
4504 unsigned int m_inputPosition;
4505 int m_continueAt;
4508 struct CRYPTOPP_DLL FilterPutSpaceHelper
4510 // desiredSize is how much to ask target, bufferSize is how much to allocate in m_tempSpace
4511 byte *HelpCreatePutSpace(BufferedTransformation &target, const std::string &channel, unsigned int minSize, unsigned int desiredSize, unsigned int &bufferSize)
4513 assert(desiredSize >= minSize && bufferSize >= minSize);
4514 if (m_tempSpace.size() < minSize)
4516 byte *result = target.ChannelCreatePutSpace(channel, desiredSize);
4517 if (desiredSize >= minSize)
4519 bufferSize = desiredSize;
4520 return result;
4522 m_tempSpace.New(bufferSize);
4525 bufferSize = m_tempSpace.size();
4526 return m_tempSpace.begin();
4528 byte *HelpCreatePutSpace(BufferedTransformation &target, const std::string &channel, unsigned int minSize)
4529 {return HelpCreatePutSpace(target, channel, minSize, minSize, minSize);}
4530 byte *HelpCreatePutSpace(BufferedTransformation &target, const std::string &channel, unsigned int minSize, unsigned int bufferSize)
4531 {return HelpCreatePutSpace(target, channel, minSize, minSize, bufferSize);}
4532 SecByteBlock m_tempSpace;
4535 /*! FilterWithBufferedInput divides up the input stream into
4536 a first block, a number of middle blocks, and a last block.
4537 First and last blocks are optional, and middle blocks may
4538 be a stream instead (i.e. blockSize == 1).
4540 class CRYPTOPP_DLL FilterWithBufferedInput : public Filter
4542 public:
4543 FilterWithBufferedInput(BufferedTransformation *attachment);
4544 //! firstSize and lastSize may be 0, blockSize must be at least 1
4545 FilterWithBufferedInput(unsigned int firstSize, unsigned int blockSize, unsigned int lastSize, BufferedTransformation *attachment);
4547 void IsolatedInitialize(const NameValuePairs &parameters);
4548 unsigned int Put2(const byte *inString, unsigned int length, int messageEnd, bool blocking)
4550 return PutMaybeModifiable(const_cast<byte *>(inString), length, messageEnd, blocking, false);
4552 unsigned int PutModifiable2(byte *inString, unsigned int length, int messageEnd, bool blocking)
4554 return PutMaybeModifiable(inString, length, messageEnd, blocking, true);
4556 /*! calls ForceNextPut() if hardFlush is true */
4557 bool IsolatedFlush(bool hardFlush, bool blocking);
4559 /*! The input buffer may contain more than blockSize bytes if lastSize != 0.
4560 ForceNextPut() forces a call to NextPut() if this is the case.
4562 void ForceNextPut();
4564 protected:
4565 bool DidFirstPut() {return m_firstInputDone;}
4567 virtual void InitializeDerivedAndReturnNewSizes(const NameValuePairs& parameters, unsigned int& /* firstSize */, unsigned int& /* blockSize */, unsigned int& /* lastSize */)
4568 {InitializeDerived(parameters);}
4569 virtual void InitializeDerived(const NameValuePairs& /* parameters */) {}
4570 // FirstPut() is called if (firstSize != 0 and totalLength >= firstSize)
4571 // or (firstSize == 0 and (totalLength > 0 or a MessageEnd() is received))
4572 virtual void FirstPut(const byte *inString) =0;
4573 // NextPut() is called if totalLength >= firstSize+blockSize+lastSize
4574 virtual void NextPutSingle(const byte* /* inString */) {assert(false);}
4575 // Same as NextPut() except length can be a multiple of blockSize
4576 // Either NextPut() or NextPutMultiple() must be overriden
4577 virtual void NextPutMultiple(const byte *inString, unsigned int length);
4578 // Same as NextPutMultiple(), but inString can be modified
4579 virtual void NextPutModifiable(byte *inString, unsigned int length)
4580 {NextPutMultiple(inString, length);}
4581 // LastPut() is always called
4582 // if totalLength < firstSize then length == totalLength
4583 // else if totalLength <= firstSize+lastSize then length == totalLength-firstSize
4584 // else lastSize <= length < lastSize+blockSize
4585 virtual void LastPut(const byte *inString, unsigned int length) =0;
4586 virtual void FlushDerived() {}
4588 private:
4589 unsigned int PutMaybeModifiable(byte *begin, unsigned int length, int messageEnd, bool blocking, bool modifiable);
4590 void NextPutMaybeModifiable(byte *inString, unsigned int length, bool modifiable)
4592 if (modifiable) NextPutModifiable(inString, length);
4593 else NextPutMultiple(inString, length);
4596 // This function should no longer be used, put this here to cause a compiler error
4597 // if someone tries to override NextPut().
4598 virtual int NextPut(const byte* /* inString */, unsigned int /* length */) {assert(false); return 0;}
4600 class BlockQueue
4602 public:
4603 void ResetQueue(unsigned int blockSize, unsigned int maxBlocks);
4604 byte *GetBlock();
4605 byte *GetContigousBlocks(unsigned int &numberOfBytes);
4606 unsigned int GetAll(byte *outString);
4607 void Put(const byte *inString, unsigned int length);
4608 unsigned int CurrentSize() const {return m_size;}
4609 unsigned int MaxSize() const {return m_buffer.size();}
4611 private:
4612 SecByteBlock m_buffer;
4613 unsigned int m_blockSize, m_maxBlocks, m_size;
4614 byte *m_begin;
4617 unsigned int m_firstSize, m_blockSize, m_lastSize;
4618 bool m_firstInputDone;
4619 BlockQueue m_queue;
4622 //! Filter Wrapper for HashTransformation
4623 class CRYPTOPP_DLL HashFilter : public Bufferless<Filter>, private FilterPutSpaceHelper
4625 public:
4626 HashFilter(HashTransformation &hm, BufferedTransformation *attachment = NULL, bool putMessage=false)
4627 : m_hashModule(hm), m_putMessage(putMessage) {Detach(attachment);}
4629 void IsolatedInitialize(const NameValuePairs &parameters);
4630 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking);
4632 byte * CreatePutSpace(unsigned int &size) {return m_hashModule.CreateUpdateSpace(size);}
4634 private:
4635 HashTransformation &m_hashModule;
4636 bool m_putMessage;
4637 byte *m_space;
4640 // Used By ProxyFilter
4641 class CRYPTOPP_DLL OutputProxy : public CustomSignalPropagation<Sink>
4643 public:
4644 OutputProxy(BufferedTransformation &owner, bool passSignal) : m_owner(owner), m_passSignal(passSignal) {}
4646 bool GetPassSignal() const {return m_passSignal;}
4647 void SetPassSignal(bool passSignal) {m_passSignal = passSignal;}
4649 byte * CreatePutSpace(unsigned int &size)
4650 {return m_owner.AttachedTransformation()->CreatePutSpace(size);}
4651 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking)
4652 {return m_owner.AttachedTransformation()->Put2(begin, length, m_passSignal ? messageEnd : 0, blocking);}
4653 unsigned int PutModifiable2(byte *begin, unsigned int length, int messageEnd, bool blocking)
4654 {return m_owner.AttachedTransformation()->PutModifiable2(begin, length, m_passSignal ? messageEnd : 0, blocking);}
4655 void Initialize(const NameValuePairs &parameters=g_nullNameValuePairs, int propagation=-1)
4656 {if (m_passSignal) m_owner.AttachedTransformation()->Initialize(parameters, propagation);}
4657 bool Flush(bool hardFlush, int propagation=-1, bool blocking=true)
4658 {return m_passSignal ? m_owner.AttachedTransformation()->Flush(hardFlush, propagation, blocking) : false;}
4659 bool MessageSeriesEnd(int propagation=-1, bool blocking=true)
4660 {return m_passSignal ? m_owner.AttachedTransformation()->MessageSeriesEnd(propagation, blocking) : false;}
4662 unsigned int ChannelPut2(const std::string &channel, const byte *begin, unsigned int length, int messageEnd, bool blocking)
4663 {return m_owner.AttachedTransformation()->ChannelPut2(channel, begin, length, m_passSignal ? messageEnd : 0, blocking);}
4664 unsigned int ChannelPutModifiable2(const std::string &channel, byte *begin, unsigned int length, int messageEnd, bool blocking)
4665 {return m_owner.AttachedTransformation()->ChannelPutModifiable2(channel, begin, length, m_passSignal ? messageEnd : 0, blocking);}
4666 bool ChannelFlush(const std::string &channel, bool completeFlush, int propagation=-1, bool blocking=true)
4667 {return m_passSignal ? m_owner.AttachedTransformation()->ChannelFlush(channel, completeFlush, propagation, blocking) : false;}
4668 bool ChannelMessageSeriesEnd(const std::string &channel, int propagation=-1, bool blocking=true)
4669 {return m_passSignal ? m_owner.AttachedTransformation()->ChannelMessageSeriesEnd(channel, propagation, blocking) : false;}
4671 private:
4672 BufferedTransformation &m_owner;
4673 bool m_passSignal;
4676 //! Base class for Filter classes that are proxies for a chain of other filters.
4677 class CRYPTOPP_DLL ProxyFilter : public FilterWithBufferedInput
4679 public:
4680 ProxyFilter(BufferedTransformation *filter, unsigned int firstSize, unsigned int lastSize, BufferedTransformation *attachment);
4682 bool IsolatedFlush(bool hardFlush, bool blocking);
4684 void SetFilter(Filter *filter);
4685 void NextPutMultiple(const byte *s, unsigned int len);
4686 void NextPutModifiable(byte *inString, unsigned int length);
4688 protected:
4689 member_ptr<BufferedTransformation> m_filter;
4692 //! simple proxy filter that doesn't modify the underlying filter's input or output
4693 class CRYPTOPP_DLL SimpleProxyFilter : public ProxyFilter
4695 public:
4696 SimpleProxyFilter(BufferedTransformation *filter, BufferedTransformation *attachment)
4697 : ProxyFilter(filter, 0, 0, attachment) {}
4699 void FirstPut(const byte *) {}
4700 void LastPut(const byte *, unsigned int) {m_filter->MessageEnd();}
4703 //! Append input to a string object
4704 template <class T>
4705 class StringSinkTemplate : public Bufferless<Sink>
4707 public:
4708 // VC60 workaround: no T::char_type
4709 typedef typename T::traits_type::char_type char_type;
4711 StringSinkTemplate(T &output)
4712 : m_output(&output) {assert(sizeof(output[0])==1);}
4714 void IsolatedInitialize(const NameValuePairs &parameters)
4715 {if (!parameters.GetValue("OutputStringPointer", m_output)) throw InvalidArgument("StringSink: OutputStringPointer not specified");}
4717 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking)
4719 if (length > 0)
4721 typename T::size_type size = m_output->size();
4722 if (length < size && size + length > m_output->capacity())
4723 m_output->reserve(2*size);
4724 m_output->append((const char_type *)begin, (const char_type *)begin+length);
4726 return 0;
4729 private:
4730 T *m_output;
4733 //! Append input to an std::string
4734 typedef StringSinkTemplate<std::string> StringSink;
4736 //! Copy input to a memory buffer
4737 class CRYPTOPP_DLL ArraySink : public Bufferless<Sink>
4739 public:
4740 ArraySink(const NameValuePairs &parameters = g_nullNameValuePairs) {IsolatedInitialize(parameters);}
4741 ArraySink(byte *buf, unsigned int size) : m_buf(buf), m_size(size), m_total(0) {}
4743 unsigned int AvailableSize() {return m_size - STDMIN(m_total, (unsigned long)m_size);}
4744 unsigned long TotalPutLength() {return m_total;}
4746 void IsolatedInitialize(const NameValuePairs &parameters);
4747 byte * CreatePutSpace(unsigned int &size);
4748 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking);
4750 protected:
4751 byte *m_buf;
4752 unsigned int m_size;
4753 unsigned long m_total;
4756 //! Xor input to a memory buffer
4757 class CRYPTOPP_DLL ArrayXorSink : public ArraySink
4759 public:
4760 ArrayXorSink(byte *buf, unsigned int size)
4761 : ArraySink(buf, size) {}
4763 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking);
4764 byte * CreatePutSpace(unsigned int &size) {return BufferedTransformation::CreatePutSpace(size);}
4767 //! string-based implementation of Store interface
4768 class StringStore : public Store
4770 public:
4771 StringStore(const char *string = NULL)
4772 {StoreInitialize(MakeParameters("InputBuffer", ConstByteArrayParameter(string)));}
4773 StringStore(const byte *string, unsigned int length)
4774 {StoreInitialize(MakeParameters("InputBuffer", ConstByteArrayParameter(string, length)));}
4775 template <class T> StringStore(const T &string)
4776 {StoreInitialize(MakeParameters("InputBuffer", ConstByteArrayParameter(string)));}
4778 CRYPTOPP_DLL unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
4779 CRYPTOPP_DLL unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const;
4781 private:
4782 CRYPTOPP_DLL void StoreInitialize(const NameValuePairs &parameters);
4784 const byte *m_store;
4785 unsigned int m_length, m_count;
4788 //! A Filter that pumps data into its attachment as input
4789 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE Source : public InputRejecting<Filter>
4791 public:
4792 Source(BufferedTransformation *attachment = NULL)
4793 {Source::Detach(attachment);}
4795 unsigned long Pump(unsigned long pumpMax=ULONG_MAX)
4796 {Pump2(pumpMax); return pumpMax;}
4797 unsigned int PumpMessages(unsigned int count=UINT_MAX)
4798 {PumpMessages2(count); return count;}
4799 void PumpAll()
4800 {PumpAll2();}
4801 virtual unsigned int Pump2(unsigned long &byteCount, bool blocking=true) =0;
4802 virtual unsigned int PumpMessages2(unsigned int &messageCount, bool blocking=true) =0;
4803 virtual unsigned int PumpAll2(bool blocking=true);
4804 virtual bool SourceExhausted() const =0;
4806 protected:
4807 void SourceInitialize(bool pumpAll, const NameValuePairs &parameters)
4809 IsolatedInitialize(parameters);
4810 if (pumpAll)
4811 PumpAll();
4815 //! Turn a Store into a Source
4816 template <class T>
4817 class SourceTemplate : public Source
4819 public:
4820 SourceTemplate<T>(BufferedTransformation *attachment)
4821 : Source(attachment) {}
4822 void IsolatedInitialize(const NameValuePairs &parameters)
4823 {m_store.IsolatedInitialize(parameters);}
4824 unsigned int Pump2(unsigned long &byteCount, bool blocking=true)
4825 {return m_store.TransferTo2(*AttachedTransformation(), byteCount, NULL_CHANNEL, blocking);}
4826 unsigned int PumpMessages2(unsigned int &messageCount, bool blocking=true)
4827 {return m_store.TransferMessagesTo2(*AttachedTransformation(), messageCount, NULL_CHANNEL, blocking);}
4828 unsigned int PumpAll2(bool blocking=true)
4829 {return m_store.TransferAllTo2(*AttachedTransformation(), NULL_CHANNEL, blocking);}
4830 bool SourceExhausted() const
4831 {return !m_store.AnyRetrievable() && !m_store.AnyMessages();}
4832 void SetAutoSignalPropagation(int propagation)
4833 {m_store.SetAutoSignalPropagation(propagation);}
4834 int GetAutoSignalPropagation() const
4835 {return m_store.GetAutoSignalPropagation();}
4837 protected:
4838 T m_store;
4841 //! string-based implementation of Source interface
4842 class CRYPTOPP_DLL StringSource : public SourceTemplate<StringStore>
4844 public:
4845 StringSource(BufferedTransformation *attachment = NULL)
4846 : SourceTemplate<StringStore>(attachment) {}
4847 StringSource(const char *string, bool pumpAll, BufferedTransformation *attachment = NULL)
4848 : SourceTemplate<StringStore>(attachment) {SourceInitialize(pumpAll, MakeParameters("InputBuffer", ConstByteArrayParameter(string)));}
4849 StringSource(const byte *string, unsigned int length, bool pumpAll, BufferedTransformation *attachment = NULL)
4850 : SourceTemplate<StringStore>(attachment) {SourceInitialize(pumpAll, MakeParameters("InputBuffer", ConstByteArrayParameter(string, length)));}
4851 StringSource(const std::string &string, bool pumpAll, BufferedTransformation *attachment = NULL)
4852 : SourceTemplate<StringStore>(attachment) {SourceInitialize(pumpAll, MakeParameters("InputBuffer", ConstByteArrayParameter(string)));}
4855 NAMESPACE_END
4857 #endif
4858 ////////////////////////////////////////////////////////////////////////////////
4862 ////////////////////////////////////////////////////////////////////////////////
4863 #ifndef CRYPTOPP_ARGNAMES_H
4864 #define CRYPTOPP_ARGNAMES_H
4866 //- #include "cryptlib.h"
4868 NAMESPACE_BEGIN(CryptoPP)
4870 DOCUMENTED_NAMESPACE_BEGIN(Name)
4872 #define CRYPTOPP_DEFINE_NAME_STRING(name) inline const char *name() {return #name;}
4874 CRYPTOPP_DEFINE_NAME_STRING(ValueNames) //!< string, a list of value names with a semicolon (';') after each name
4875 CRYPTOPP_DEFINE_NAME_STRING(Version) //!< int
4876 CRYPTOPP_DEFINE_NAME_STRING(Seed) //!< ConstByteArrayParameter
4877 CRYPTOPP_DEFINE_NAME_STRING(Key) //!< ConstByteArrayParameter
4878 CRYPTOPP_DEFINE_NAME_STRING(IV) //!< const byte *
4879 CRYPTOPP_DEFINE_NAME_STRING(StolenIV) //!< byte *
4880 CRYPTOPP_DEFINE_NAME_STRING(Rounds) //!< int
4881 CRYPTOPP_DEFINE_NAME_STRING(FeedbackSize) //!< int
4882 CRYPTOPP_DEFINE_NAME_STRING(WordSize) //!< int, in bytes
4883 CRYPTOPP_DEFINE_NAME_STRING(BlockSize) //!< int, in bytes
4884 CRYPTOPP_DEFINE_NAME_STRING(EffectiveKeyLength) //!< int, in bits
4885 CRYPTOPP_DEFINE_NAME_STRING(KeySize) //!< int, in bits
4886 CRYPTOPP_DEFINE_NAME_STRING(ModulusSize) //!< int, in bits
4887 CRYPTOPP_DEFINE_NAME_STRING(SubgroupOrderSize) //!< int, in bits
4888 CRYPTOPP_DEFINE_NAME_STRING(PrivateExponentSize)//!< int, in bits
4889 CRYPTOPP_DEFINE_NAME_STRING(Modulus) //!< Integer
4890 CRYPTOPP_DEFINE_NAME_STRING(PublicExponent) //!< Integer
4891 CRYPTOPP_DEFINE_NAME_STRING(PrivateExponent) //!< Integer
4892 CRYPTOPP_DEFINE_NAME_STRING(PublicElement) //!< Integer
4893 CRYPTOPP_DEFINE_NAME_STRING(SubgroupOrder) //!< Integer
4894 CRYPTOPP_DEFINE_NAME_STRING(Cofactor) //!< Integer
4895 CRYPTOPP_DEFINE_NAME_STRING(SubgroupGenerator) //!< Integer, ECP::Point, or EC2N::Point
4896 CRYPTOPP_DEFINE_NAME_STRING(Curve) //!< ECP or EC2N
4897 CRYPTOPP_DEFINE_NAME_STRING(GroupOID) //!< OID
4898 CRYPTOPP_DEFINE_NAME_STRING(PointerToPrimeSelector) //!< const PrimeSelector *
4899 CRYPTOPP_DEFINE_NAME_STRING(Prime1) //!< Integer
4900 CRYPTOPP_DEFINE_NAME_STRING(Prime2) //!< Integer
4901 CRYPTOPP_DEFINE_NAME_STRING(ModPrime1PrivateExponent) //!< Integer
4902 CRYPTOPP_DEFINE_NAME_STRING(ModPrime2PrivateExponent) //!< Integer
4903 CRYPTOPP_DEFINE_NAME_STRING(MultiplicativeInverseOfPrime2ModPrime1) //!< Integer
4904 CRYPTOPP_DEFINE_NAME_STRING(QuadraticResidueModPrime1) //!< Integer
4905 CRYPTOPP_DEFINE_NAME_STRING(QuadraticResidueModPrime2) //!< Integer
4906 CRYPTOPP_DEFINE_NAME_STRING(PutMessage) //!< bool
4907 CRYPTOPP_DEFINE_NAME_STRING(HashVerificationFilterFlags) //!< word32
4908 CRYPTOPP_DEFINE_NAME_STRING(SignatureVerificationFilterFlags) //!< word32
4909 CRYPTOPP_DEFINE_NAME_STRING(InputBuffer) //!< ConstByteArrayParameter
4910 CRYPTOPP_DEFINE_NAME_STRING(OutputBuffer) //!< ByteArrayParameter
4911 CRYPTOPP_DEFINE_NAME_STRING(XMACC_Counter) //!< word32
4912 CRYPTOPP_DEFINE_NAME_STRING(InputFileName) //!< const char *
4913 CRYPTOPP_DEFINE_NAME_STRING(InputStreamPointer) //!< std::istream *
4914 CRYPTOPP_DEFINE_NAME_STRING(InputBinaryMode) //!< bool
4915 CRYPTOPP_DEFINE_NAME_STRING(OutputFileName) //!< const char *
4916 CRYPTOPP_DEFINE_NAME_STRING(OutputStreamPointer) //!< std::ostream *
4917 CRYPTOPP_DEFINE_NAME_STRING(OutputBinaryMode) //!< bool
4918 CRYPTOPP_DEFINE_NAME_STRING(EncodingParameters) //!< ConstByteArrayParameter
4919 CRYPTOPP_DEFINE_NAME_STRING(KeyDerivationParameters) //!< ConstByteArrayParameter
4920 CRYPTOPP_DEFINE_NAME_STRING(Separator) //< ConstByteArrayParameter
4921 CRYPTOPP_DEFINE_NAME_STRING(Terminator) //< ConstByteArrayParameter
4922 CRYPTOPP_DEFINE_NAME_STRING(Uppercase) //< bool
4923 CRYPTOPP_DEFINE_NAME_STRING(GroupSize) //< int
4924 CRYPTOPP_DEFINE_NAME_STRING(Pad) //< bool
4925 CRYPTOPP_DEFINE_NAME_STRING(PaddingByte) //< byte
4926 CRYPTOPP_DEFINE_NAME_STRING(Log2Base) //< int
4927 CRYPTOPP_DEFINE_NAME_STRING(EncodingLookupArray) //< const byte *
4928 CRYPTOPP_DEFINE_NAME_STRING(DecodingLookupArray) //< const byte *
4929 CRYPTOPP_DEFINE_NAME_STRING(InsertLineBreaks) //< bool
4930 CRYPTOPP_DEFINE_NAME_STRING(MaxLineLength) //< int
4932 DOCUMENTED_NAMESPACE_END
4934 NAMESPACE_END
4936 #endif
4937 ////////////////////////////////////////////////////////////////////////////////
4940 ////////////////////////////////////////////////////////////////////////////////
4941 // pubkey.h - written and placed in the public domain by Wei Dai
4943 #ifndef CRYPTOPP_PUBKEY_H
4944 #define CRYPTOPP_PUBKEY_H
4946 /** \file
4948 This file contains helper classes/functions for implementing public key algorithms.
4950 The class hierachies in this .h file tend to look like this:
4951 <pre>
4954 y1 z1
4956 x2<y1> x2<z1>
4958 y2 z2
4960 x3<y2> x3<z2>
4962 y3 z3
4963 </pre>
4964 - x1, y1, z1 are abstract interface classes defined in cryptlib.h
4965 - x2, y2, z2 are implementations of the interfaces using "abstract policies", which
4966 are pure virtual functions that should return interfaces to interchangeable algorithms.
4967 These classes have "Base" suffixes.
4968 - x3, y3, z3 hold actual algorithms and implement those virtual functions.
4969 These classes have "Impl" suffixes.
4971 The "TF_" prefix means an implementation using trapdoor functions on integers.
4972 The "DL_" prefix means an implementation using group operations (in groups where discrete log is hard).
4975 //- #include "modarith.h"
4976 //- #include "filters.h"
4977 //- #include "eprecomp.h"
4978 //- #include "fips140.h"
4979 //- #include "argnames.h"
4980 #include <memory>
4982 // VC60 workaround: this macro is defined in shlobj.h and conflicts with a template parameter used in this file
4983 #undef INTERFACE
4985 NAMESPACE_BEGIN(CryptoPP)
4987 //! _
4988 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE TrapdoorFunctionBounds
4990 public:
4991 virtual ~TrapdoorFunctionBounds() {}
4993 virtual Integer PreimageBound() const =0;
4994 virtual Integer ImageBound() const =0;
4995 virtual Integer MaxPreimage() const {return --PreimageBound();}
4996 virtual Integer MaxImage() const {return --ImageBound();}
4999 //! _
5000 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE RandomizedTrapdoorFunction : public TrapdoorFunctionBounds
5002 public:
5003 virtual Integer ApplyRandomizedFunction(RandomNumberGenerator &rng, const Integer &x) const =0;
5004 virtual bool IsRandomized() const {return true;}
5007 //! _
5008 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE TrapdoorFunction : public RandomizedTrapdoorFunction
5010 public:
5011 Integer ApplyRandomizedFunction(RandomNumberGenerator& /* rng */, const Integer &x) const
5012 {return ApplyFunction(x);}
5013 bool IsRandomized() const {return false;}
5015 virtual Integer ApplyFunction(const Integer &x) const =0;
5018 //! _
5019 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE RandomizedTrapdoorFunctionInverse
5021 public:
5022 virtual ~RandomizedTrapdoorFunctionInverse() {}
5024 virtual Integer CalculateRandomizedInverse(RandomNumberGenerator &rng, const Integer &x) const =0;
5025 virtual bool IsRandomized() const {return true;}
5028 //! _
5029 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE TrapdoorFunctionInverse : public RandomizedTrapdoorFunctionInverse
5031 public:
5032 virtual ~TrapdoorFunctionInverse() {}
5034 Integer CalculateRandomizedInverse(RandomNumberGenerator &rng, const Integer &x) const
5035 {return CalculateInverse(rng, x);}
5036 bool IsRandomized() const {return false;}
5038 virtual Integer CalculateInverse(RandomNumberGenerator &rng, const Integer &x) const =0;
5041 // ********************************************************
5043 //! message encoding method for public key encryption
5044 class CRYPTOPP_NO_VTABLE PK_EncryptionMessageEncodingMethod
5046 public:
5047 virtual ~PK_EncryptionMessageEncodingMethod() {}
5049 virtual bool ParameterSupported(const char* /* name */) const {return false;}
5051 //! max size of unpadded message in bytes, given max size of padded message in bits (1 less than size of modulus)
5052 virtual unsigned int MaxUnpaddedLength(unsigned int paddedLength) const =0;
5054 virtual void Pad(RandomNumberGenerator &rng, const byte *raw, unsigned int inputLength, byte *padded, unsigned int paddedBitLength, const NameValuePairs &parameters) const =0;
5056 virtual DecodingResult Unpad(const byte *padded, unsigned int paddedBitLength, byte *raw, const NameValuePairs &parameters) const =0;
5059 // ********************************************************
5061 //! _
5062 template <class TFI, class MEI>
5063 class CRYPTOPP_NO_VTABLE TF_Base
5065 protected:
5066 virtual ~TF_Base() {};
5068 virtual const TrapdoorFunctionBounds & GetTrapdoorFunctionBounds() const =0;
5070 typedef TFI TrapdoorFunctionInterface;
5071 virtual const TrapdoorFunctionInterface & GetTrapdoorFunctionInterface() const =0;
5073 typedef MEI MessageEncodingInterface;
5074 virtual const MessageEncodingInterface & GetMessageEncodingInterface() const =0;
5077 // ********************************************************
5079 typedef std::pair<const byte *, unsigned int> HashIdentifier;
5081 //! interface for message encoding method for public key signature schemes
5082 class CRYPTOPP_NO_VTABLE PK_SignatureMessageEncodingMethod
5084 public:
5085 virtual ~PK_SignatureMessageEncodingMethod() {}
5087 virtual unsigned int MaxRecoverableLength(unsigned int /* representativeBitLength */, unsigned int /* hashIdentifierLength */, unsigned int /* digestLength */) const
5088 {return 0;}
5090 bool IsProbabilistic() const
5091 {return true;}
5092 bool AllowNonrecoverablePart() const
5093 {throw NotImplemented("PK_MessageEncodingMethod: this signature scheme does not support message recovery");}
5094 virtual bool RecoverablePartFirst() const
5095 {throw NotImplemented("PK_MessageEncodingMethod: this signature scheme does not support message recovery");}
5097 // for verification, DL
5098 virtual void ProcessSemisignature(HashTransformation& /* hash */, const byte* /* semisignature */, unsigned int /* semisignatureLength */) const {}
5100 // for signature
5101 virtual void ProcessRecoverableMessage(HashTransformation& /* hash */,
5102 const byte* /* recoverableMessage */, unsigned int /* recoverableMessageLength */,
5103 const byte* /* presignature */, unsigned int /* presignatureLength */,
5104 SecByteBlock& /* semisignature */) const
5106 if (RecoverablePartFirst())
5107 assert(!"ProcessRecoverableMessage() not implemented");
5110 virtual void ComputeMessageRepresentative(RandomNumberGenerator &rng,
5111 const byte *recoverableMessage, unsigned int recoverableMessageLength,
5112 HashTransformation &hash, HashIdentifier hashIdentifier, bool messageEmpty,
5113 byte *representative, unsigned int representativeBitLength) const =0;
5115 virtual bool VerifyMessageRepresentative(
5116 HashTransformation &hash, HashIdentifier hashIdentifier, bool messageEmpty,
5117 byte *representative, unsigned int representativeBitLength) const =0;
5119 virtual DecodingResult RecoverMessageFromRepresentative( // for TF
5120 HashTransformation& /* hash */, HashIdentifier /* hashIdentifier */, bool /* messageEmpty */,
5121 byte* /* representative */, unsigned int /* representativeBitLength */,
5122 byte* /* recoveredMessage */) const
5123 {throw NotImplemented("PK_MessageEncodingMethod: this signature scheme does not support message recovery");}
5125 virtual DecodingResult RecoverMessageFromSemisignature( // for DL
5126 HashTransformation& /* hash */, HashIdentifier /* hashIdentifier */,
5127 const byte* /* presignature */, unsigned int /* presignatureLength */,
5128 const byte* /* semisignature */, unsigned int /* semisignatureLength */,
5129 byte* /* recoveredMessage */) const
5130 {throw NotImplemented("PK_MessageEncodingMethod: this signature scheme does not support message recovery");}
5132 // VC60 workaround
5133 struct HashIdentifierLookup
5135 template <class H> struct HashIdentifierLookup2
5137 static HashIdentifier Lookup()
5139 return HashIdentifier(NULL, 0);
5145 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_DeterministicSignatureMessageEncodingMethod : public PK_SignatureMessageEncodingMethod
5147 public:
5148 bool VerifyMessageRepresentative(
5149 HashTransformation &hash, HashIdentifier hashIdentifier, bool messageEmpty,
5150 byte *representative, unsigned int representativeBitLength) const;
5153 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE PK_MessageAccumulatorBase : public PK_MessageAccumulator
5155 public:
5156 PK_MessageAccumulatorBase() : m_empty(true) {}
5158 virtual HashTransformation & AccessHash() =0;
5160 void Update(const byte *input, unsigned int length)
5162 AccessHash().Update(input, length);
5163 m_empty = m_empty && length == 0;
5166 SecByteBlock m_recoverableMessage, m_representative, m_presignature, m_semisignature;
5167 Integer m_k, m_s;
5168 bool m_empty;
5171 template <class HASH_ALGORITHM>
5172 class PK_MessageAccumulatorImpl : public PK_MessageAccumulatorBase, protected ObjectHolder<HASH_ALGORITHM>
5174 public:
5175 HashTransformation & AccessHash() {return this->m_object;}
5178 //! _
5179 template <class INTERFACE, class BASE>
5180 class CRYPTOPP_NO_VTABLE TF_SignatureSchemeBase : public INTERFACE, protected BASE
5182 public:
5183 unsigned int SignatureLength() const
5184 {return this->GetTrapdoorFunctionBounds().MaxPreimage().ByteCount();}
5185 unsigned int MaxRecoverableLength() const
5186 {return this->GetMessageEncodingInterface().MaxRecoverableLength(MessageRepresentativeBitLength(), GetHashIdentifier().second, GetDigestSize());}
5187 unsigned int MaxRecoverableLengthFromSignatureLength(unsigned int /* signatureLength */) const
5188 {return this->MaxRecoverableLength();}
5190 bool IsProbabilistic() const
5191 {return this->GetTrapdoorFunctionInterface().IsRandomized() || this->GetMessageEncodingInterface().IsProbabilistic();}
5192 bool AllowNonrecoverablePart() const
5193 {return this->GetMessageEncodingInterface().AllowNonrecoverablePart();}
5194 bool RecoverablePartFirst() const
5195 {return this->GetMessageEncodingInterface().RecoverablePartFirst();}
5197 protected:
5198 unsigned int MessageRepresentativeLength() const {return BitsToBytes(MessageRepresentativeBitLength());}
5199 unsigned int MessageRepresentativeBitLength() const {return this->GetTrapdoorFunctionBounds().ImageBound().BitCount()-1;}
5200 virtual HashIdentifier GetHashIdentifier() const =0;
5201 virtual unsigned int GetDigestSize() const =0;
5204 //! _
5205 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE TF_SignerBase : public TF_SignatureSchemeBase<PK_Signer, TF_Base<RandomizedTrapdoorFunctionInverse, PK_SignatureMessageEncodingMethod> >
5207 public:
5208 void InputRecoverableMessage(PK_MessageAccumulator &messageAccumulator, const byte *recoverableMessage, unsigned int recoverableMessageLength) const;
5209 unsigned int SignAndRestart(RandomNumberGenerator &rng, PK_MessageAccumulator &messageAccumulator, byte *signature, bool restart=true) const;
5212 //! _
5213 class CRYPTOPP_DLL CRYPTOPP_NO_VTABLE TF_VerifierBase : public TF_SignatureSchemeBase<PK_Verifier, TF_Base<TrapdoorFunction, PK_SignatureMessageEncodingMethod> >
5215 public:
5216 void InputSignature(PK_MessageAccumulator &messageAccumulator, const byte *signature, unsigned int signatureLength) const;
5217 bool VerifyAndRestart(PK_MessageAccumulator &messageAccumulator) const;
5218 DecodingResult RecoverAndRestart(byte *recoveredMessage, PK_MessageAccumulator &recoveryAccumulator) const;
5221 // ********************************************************
5223 //! _
5224 template <class T1, class T2, class T3>
5225 struct TF_CryptoSchemeOptions
5227 typedef T1 AlgorithmInfo;
5228 typedef T2 Keys;
5229 typedef typename Keys::PrivateKey PrivateKey;
5230 typedef typename Keys::PublicKey PublicKey;
5231 typedef T3 MessageEncodingMethod;
5234 //! _
5235 template <class T1, class T2, class T3, class T4>
5236 struct TF_SignatureSchemeOptions : public TF_CryptoSchemeOptions<T1, T2, T3>
5238 typedef T4 HashFunction;
5241 //! _
5242 template <class KEYS>
5243 class CRYPTOPP_NO_VTABLE PublicKeyCopier
5245 public:
5246 virtual ~PublicKeyCopier() {};
5248 typedef typename KEYS::PublicKey KeyClass;
5249 virtual void CopyKeyInto(typename KEYS::PublicKey &key) const =0;
5252 //! _
5253 template <class KEYS>
5254 class CRYPTOPP_NO_VTABLE PrivateKeyCopier
5256 public:
5257 virtual ~PrivateKeyCopier() {};
5259 typedef typename KEYS::PrivateKey KeyClass;
5260 virtual void CopyKeyInto(typename KEYS::PublicKey &key) const =0;
5261 virtual void CopyKeyInto(typename KEYS::PrivateKey &key) const =0;
5264 //! _
5265 template <class BASE, class SCHEME_OPTIONS, class KEY>
5266 class CRYPTOPP_NO_VTABLE TF_ObjectImplBase : public AlgorithmImpl<BASE, typename SCHEME_OPTIONS::AlgorithmInfo>
5268 public:
5269 typedef SCHEME_OPTIONS SchemeOptions;
5270 typedef KEY KeyClass;
5272 PublicKey & AccessPublicKey() {return AccessKey();}
5273 const PublicKey & GetPublicKey() const {return GetKey();}
5275 PrivateKey & AccessPrivateKey() {return AccessKey();}
5276 const PrivateKey & GetPrivateKey() const {return GetKey();}
5278 virtual const KeyClass & GetKey() const =0;
5279 virtual KeyClass & AccessKey() =0;
5281 const KeyClass & GetTrapdoorFunction() const {return GetKey();}
5283 PK_MessageAccumulator * NewSignatureAccumulator(RandomNumberGenerator& /* rng */) const
5285 return new PK_MessageAccumulatorImpl<CPP_TYPENAME SCHEME_OPTIONS::HashFunction>;
5287 PK_MessageAccumulator * NewVerificationAccumulator() const
5289 return new PK_MessageAccumulatorImpl<CPP_TYPENAME SCHEME_OPTIONS::HashFunction>;
5292 protected:
5293 const typename BASE::MessageEncodingInterface & GetMessageEncodingInterface() const
5294 {return Singleton<CPP_TYPENAME SCHEME_OPTIONS::MessageEncodingMethod>().Ref();}
5295 const TrapdoorFunctionBounds & GetTrapdoorFunctionBounds() const
5296 {return GetKey();}
5297 const typename BASE::TrapdoorFunctionInterface & GetTrapdoorFunctionInterface() const
5298 {return GetKey();}
5300 // for signature scheme
5301 HashIdentifier GetHashIdentifier() const
5303 typedef CPP_TYPENAME SchemeOptions::MessageEncodingMethod::HashIdentifierLookup::template HashIdentifierLookup2<CPP_TYPENAME SchemeOptions::HashFunction> L;
5304 return L::Lookup();
5306 unsigned int GetDigestSize() const
5308 typedef CPP_TYPENAME SchemeOptions::HashFunction H;
5309 return H::DIGESTSIZE;
5313 //! _
5314 template <class BASE, class SCHEME_OPTIONS, class KEY_COPIER>
5315 class CRYPTOPP_NO_VTABLE TF_ObjectImpl : public TF_ObjectImplBase<TwoBases<BASE, KEY_COPIER>, SCHEME_OPTIONS, typename KEY_COPIER::KeyClass>
5317 public:
5318 typedef typename KEY_COPIER::KeyClass KeyClass;
5320 const KeyClass & GetKey() const {return m_trapdoorFunction;}
5321 KeyClass & AccessKey() {return m_trapdoorFunction;}
5323 void CopyKeyInto(typename SCHEME_OPTIONS::PrivateKey &key) const {key = GetKey();}
5324 void CopyKeyInto(typename SCHEME_OPTIONS::PublicKey &key) const {key = GetKey();}
5326 private:
5327 KeyClass m_trapdoorFunction;
5330 //! _
5331 template <class SCHEME_OPTIONS>
5332 class TF_SignerImpl : public TF_ObjectImpl<TF_SignerBase, SCHEME_OPTIONS, PrivateKeyCopier<typename SCHEME_OPTIONS::Keys> >
5336 //! _
5337 template <class SCHEME_OPTIONS>
5338 class TF_VerifierImpl : public TF_ObjectImpl<TF_VerifierBase, SCHEME_OPTIONS, PublicKeyCopier<typename SCHEME_OPTIONS::Keys> >
5342 // ********************************************************
5344 CRYPTOPP_DLL void P1363_MGF1KDF2_Common(HashTransformation &hash, byte *output, unsigned int outputLength, const byte *input, unsigned int inputLength, const byte *derivationParams, unsigned int derivationParamsLength, bool mask, unsigned int counterStart);
5346 // ********************************************************
5348 //! _
5349 template <class H>
5350 class P1363_KDF2
5352 public:
5353 static void DeriveKey(byte *output, unsigned int outputLength, const byte *input, unsigned int inputLength, const byte *derivationParams, unsigned int derivationParamsLength)
5355 H h;
5356 P1363_MGF1KDF2_Common(h, output, outputLength, input, inputLength, derivationParams, derivationParamsLength, false, 1);
5360 // ********************************************************
5362 //! A template implementing constructors for public key algorithm classes
5363 template <class BASE>
5364 class CRYPTOPP_NO_VTABLE PK_FinalTemplate : public BASE
5366 public:
5367 PK_FinalTemplate() {}
5369 PK_FinalTemplate(const Integer &v1)
5370 {this->AccessKey().Initialize(v1);}
5372 PK_FinalTemplate(const typename BASE::KeyClass &key) {this->AccessKey().operator=(key);}
5374 template <class T>
5375 PK_FinalTemplate(const PublicKeyCopier<T> &key)
5376 {key.CopyKeyInto(this->AccessKey());}
5378 template <class T>
5379 PK_FinalTemplate(const PrivateKeyCopier<T> &key)
5380 {key.CopyKeyInto(this->AccessKey());}
5382 PK_FinalTemplate(BufferedTransformation &bt) {this->AccessKey().BERDecode(bt);}
5384 #if (defined(_MSC_VER) && _MSC_VER < 1300)
5386 template <class T1, class T2>
5387 PK_FinalTemplate(T1 &v1, T2 &v2)
5388 {this->AccessKey().Initialize(v1, v2);}
5390 template <class T1, class T2, class T3>
5391 PK_FinalTemplate(T1 &v1, T2 &v2, T3 &v3)
5392 {this->AccessKey().Initialize(v1, v2, v3);}
5394 template <class T1, class T2, class T3, class T4>
5395 PK_FinalTemplate(T1 &v1, T2 &v2, T3 &v3, T4 &v4)
5396 {this->AccessKey().Initialize(v1, v2, v3, v4);}
5398 template <class T1, class T2, class T3, class T4, class T5>
5399 PK_FinalTemplate(T1 &v1, T2 &v2, T3 &v3, T4 &v4, T5 &v5)
5400 {this->AccessKey().Initialize(v1, v2, v3, v4, v5);}
5402 template <class T1, class T2, class T3, class T4, class T5, class T6>
5403 PK_FinalTemplate(T1 &v1, T2 &v2, T3 &v3, T4 &v4, T5 &v5, T6 &v6)
5404 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6);}
5406 template <class T1, class T2, class T3, class T4, class T5, class T6, class T7>
5407 PK_FinalTemplate(T1 &v1, T2 &v2, T3 &v3, T4 &v4, T5 &v5, T6 &v6, T7 &v7)
5408 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6, v7);}
5410 template <class T1, class T2, class T3, class T4, class T5, class T6, class T7, class T8>
5411 PK_FinalTemplate(T1 &v1, T2 &v2, T3 &v3, T4 &v4, T5 &v5, T6 &v6, T7 &v7, T8 &v8)
5412 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6, v7, v8);}
5414 #else
5416 template <class T1, class T2>
5417 PK_FinalTemplate(const T1 &v1, const T2 &v2)
5418 {this->AccessKey().Initialize(v1, v2);}
5420 template <class T1, class T2, class T3>
5421 PK_FinalTemplate(const T1 &v1, const T2 &v2, const T3 &v3)
5422 {this->AccessKey().Initialize(v1, v2, v3);}
5424 template <class T1, class T2, class T3, class T4>
5425 PK_FinalTemplate(const T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4)
5426 {this->AccessKey().Initialize(v1, v2, v3, v4);}
5428 template <class T1, class T2, class T3, class T4, class T5>
5429 PK_FinalTemplate(const T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5)
5430 {this->AccessKey().Initialize(v1, v2, v3, v4, v5);}
5432 template <class T1, class T2, class T3, class T4, class T5, class T6>
5433 PK_FinalTemplate(const T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5, const T6 &v6)
5434 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6);}
5436 template <class T1, class T2, class T3, class T4, class T5, class T6, class T7>
5437 PK_FinalTemplate(const T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5, const T6 &v6, const T7 &v7)
5438 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6, v7);}
5440 template <class T1, class T2, class T3, class T4, class T5, class T6, class T7, class T8>
5441 PK_FinalTemplate(const T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5, const T6 &v6, const T7 &v7, const T8 &v8)
5442 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6, v7, v8);}
5444 template <class T1, class T2>
5445 PK_FinalTemplate(T1 &v1, const T2 &v2)
5446 {this->AccessKey().Initialize(v1, v2);}
5448 template <class T1, class T2, class T3>
5449 PK_FinalTemplate(T1 &v1, const T2 &v2, const T3 &v3)
5450 {this->AccessKey().Initialize(v1, v2, v3);}
5452 template <class T1, class T2, class T3, class T4>
5453 PK_FinalTemplate(T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4)
5454 {this->AccessKey().Initialize(v1, v2, v3, v4);}
5456 template <class T1, class T2, class T3, class T4, class T5>
5457 PK_FinalTemplate(T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5)
5458 {this->AccessKey().Initialize(v1, v2, v3, v4, v5);}
5460 template <class T1, class T2, class T3, class T4, class T5, class T6>
5461 PK_FinalTemplate(T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5, const T6 &v6)
5462 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6);}
5464 template <class T1, class T2, class T3, class T4, class T5, class T6, class T7>
5465 PK_FinalTemplate(T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5, const T6 &v6, const T7 &v7)
5466 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6, v7);}
5468 template <class T1, class T2, class T3, class T4, class T5, class T6, class T7, class T8>
5469 PK_FinalTemplate(T1 &v1, const T2 &v2, const T3 &v3, const T4 &v4, const T5 &v5, const T6 &v6, const T7 &v7, const T8 &v8)
5470 {this->AccessKey().Initialize(v1, v2, v3, v4, v5, v6, v7, v8);}
5472 #endif
5475 //! Base class for public key encryption standard classes. These classes are used to select from variants of algorithms. Note that not all standards apply to all algorithms.
5476 struct EncryptionStandard {};
5478 //! Base class for public key signature standard classes. These classes are used to select from variants of algorithms. Note that not all standards apply to all algorithms.
5479 struct SignatureStandard {};
5481 template <class STANDARD, class H, class KEYS, class ALG_INFO> // VC60 workaround: doesn't work if KEYS is first parameter
5482 class TF_SS;
5484 //! Trapdoor Function Based Signature Scheme
5485 template <class STANDARD, class H, class KEYS, class ALG_INFO = TF_SS<STANDARD, H, KEYS, int> > // VC60 workaround: doesn't work if KEYS is first parameter
5486 class TF_SS : public KEYS
5488 public:
5489 //! see SignatureStandard for a list of standards
5490 typedef STANDARD Standard;
5491 typedef typename Standard::SignatureMessageEncodingMethod MessageEncodingMethod;
5492 typedef TF_SignatureSchemeOptions<ALG_INFO, KEYS, MessageEncodingMethod, H> SchemeOptions;
5494 static std::string StaticAlgorithmName() {return KEYS::StaticAlgorithmName() + "/" + MessageEncodingMethod::StaticAlgorithmName() + "(" + H::StaticAlgorithmName() + ")";}
5496 //! implements PK_Signer interface
5497 typedef PK_FinalTemplate<TF_SignerImpl<SchemeOptions> > Signer;
5498 //! implements PK_Verifier interface
5499 typedef PK_FinalTemplate<TF_VerifierImpl<SchemeOptions> > Verifier;
5502 NAMESPACE_END
5504 #endif
5505 ////////////////////////////////////////////////////////////////////////////////
5509 ////////////////////////////////////////////////////////////////////////////////
5510 #ifndef CRYPTOPP_ITERHASH_H
5511 #define CRYPTOPP_ITERHASH_H
5513 //- #include "cryptlib.h"
5514 //- #include "secblock.h"
5515 //- #include "misc.h"
5516 //- #include "simple.h"
5518 NAMESPACE_BEGIN(CryptoPP)
5520 //! _
5521 template <class T, class BASE>
5522 class CRYPTOPP_NO_VTABLE IteratedHashBase : public BASE
5524 public:
5525 typedef T HashWordType;
5527 IteratedHashBase() : m_countLo(0), m_countHi(0) {}
5528 unsigned int BlockSize() const {return m_data.size() * sizeof(T);}
5529 unsigned int OptimalBlockSize() const {return BlockSize();}
5530 unsigned int OptimalDataAlignment() const {return sizeof(T);}
5531 void Update(const byte *input, unsigned int length);
5532 byte * CreateUpdateSpace(unsigned int &size);
5533 void Restart();
5535 protected:
5536 void SetBlockSize(unsigned int blockSize) {m_data.resize(blockSize / sizeof(HashWordType));}
5537 void SetStateSize(unsigned int stateSize) {m_digest.resize(stateSize / sizeof(HashWordType));}
5539 T GetBitCountHi() const {return (m_countLo >> (8*sizeof(T)-3)) + (m_countHi << 3);}
5540 T GetBitCountLo() const {return m_countLo << 3;}
5542 virtual unsigned int HashMultipleBlocks(const T *input, unsigned int length);
5543 void PadLastBlock(unsigned int lastBlockSize, byte padFirst=0x80);
5544 virtual void Init() =0;
5545 virtual void HashBlock(const T *input) =0;
5547 SecBlock<T> m_data; // Data buffer
5548 SecBlock<T> m_digest; // Message digest
5550 private:
5551 T m_countLo, m_countHi;
5555 //! _
5556 template <class T, class B, class BASE>
5557 class CRYPTOPP_NO_VTABLE IteratedHashBase2 : public IteratedHashBase<T, BASE>
5559 public:
5560 typedef B ByteOrderClass;
5561 typedef typename IteratedHashBase<T, BASE>::HashWordType HashWordType;
5563 inline static void CorrectEndianess(HashWordType *out, const HashWordType *in, unsigned int byteCount)
5565 ConditionalByteReverse(B::ToEnum(), out, in, byteCount);
5568 void TruncatedFinal(byte *digest, unsigned int size);
5570 protected:
5571 void HashBlock(const HashWordType *input);
5572 virtual void HashEndianCorrectedBlock(const HashWordType *data) =0;
5575 //! _
5576 template <class T_HashWordType, class T_Endianness, unsigned int T_BlockSize, class T_Base = HashTransformation>
5577 class CRYPTOPP_NO_VTABLE IteratedHash : public IteratedHashBase2<T_HashWordType, T_Endianness, T_Base>
5579 public:
5580 enum {BLOCKSIZE = T_BlockSize};
5581 CRYPTOPP_COMPILE_ASSERT_GLOBAL((BLOCKSIZE & (BLOCKSIZE - 1)) == 0); // blockSize is a power of 2
5583 protected:
5584 IteratedHash()
5585 : IteratedHashBase2<T_HashWordType, T_Endianness, T_Base>()
5586 {this->SetBlockSize(T_BlockSize);}
5589 //! _
5590 template <class T_HashWordType, class T_Endianness, unsigned int T_BlockSize, unsigned int T_StateSize, class T_Transform, unsigned int T_DigestSize = T_StateSize>
5591 class CRYPTOPP_NO_VTABLE IteratedHashWithStaticTransform
5592 : public ClonableImpl<T_Transform, AlgorithmImpl<IteratedHash<T_HashWordType, T_Endianness, T_BlockSize>, T_Transform> >
5594 public:
5595 enum {DIGESTSIZE = T_DigestSize};
5596 unsigned int DigestSize() const {return DIGESTSIZE;};
5598 protected:
5599 IteratedHashWithStaticTransform()
5601 this->SetStateSize(T_StateSize);
5602 Init();
5604 void HashEndianCorrectedBlock(const T_HashWordType *data) {T_Transform::Transform(this->m_digest, data);}
5605 void Init() {T_Transform::InitState(this->m_digest);}
5608 // *************************************************************
5610 template <class T, class B, class BASE> void IteratedHashBase2<T, B, BASE>::TruncatedFinal(byte *digest, unsigned int size)
5612 this->ThrowIfInvalidTruncatedSize(size);
5614 PadLastBlock(this->BlockSize() - 2*sizeof(HashWordType));
5615 CorrectEndianess(this->m_data, this->m_data, this->BlockSize() - 2*sizeof(HashWordType));
5617 this->m_data[this->m_data.size()-2] = B::ToEnum() ? this->GetBitCountHi() : this->GetBitCountLo();
5618 this->m_data[this->m_data.size()-1] = B::ToEnum() ? this->GetBitCountLo() : this->GetBitCountHi();
5620 HashEndianCorrectedBlock(this->m_data);
5621 CorrectEndianess(this->m_digest, this->m_digest, this->DigestSize());
5622 memcpy(digest, this->m_digest, size);
5624 this->Restart(); // reinit for next use
5627 template <class T, class B, class BASE> void IteratedHashBase2<T, B, BASE>::HashBlock(const HashWordType *input)
5629 if (NativeByteOrderIs(B::ToEnum()))
5630 HashEndianCorrectedBlock(input);
5631 else
5633 ByteReverse(this->m_data.begin(), input, this->BlockSize());
5634 HashEndianCorrectedBlock(this->m_data);
5638 NAMESPACE_END
5640 #endif
5641 ////////////////////////////////////////////////////////////////////////////////
5645 ////////////////////////////////////////////////////////////////////////////////
5646 #ifndef CRYPTOPP_SHA_H
5647 #define CRYPTOPP_SHA_H
5649 //- #include "iterhash.h"
5651 NAMESPACE_BEGIN(CryptoPP)
5653 /// <a href="http://www.weidai.com/scan-mirror/md.html#SHA-1">SHA-1</a>
5654 class CRYPTOPP_DLL SHA : public IteratedHashWithStaticTransform<word32, BigEndian, 64, 20, SHA>
5656 public:
5657 static void InitState(HashWordType *state);
5658 static void Transform(word32 *digest, const word32 *data);
5659 static const char *StaticAlgorithmName() {return "SHA-1";}
5662 typedef SHA SHA1;
5664 NAMESPACE_END
5666 #endif
5667 ////////////////////////////////////////////////////////////////////////////////
5671 ////////////////////////////////////////////////////////////////////////////////
5672 #ifndef CRYPTOPP_PKCSPAD_H
5673 #define CRYPTOPP_PKCSPAD_H
5675 //- #include "cryptlib.h"
5676 //- #include "pubkey.h"
5678 #ifdef CRYPTOPP_IS_DLL
5679 //- #include "sha.h"
5680 #endif
5682 NAMESPACE_BEGIN(CryptoPP)
5684 //! <a href="http://www.weidai.com/scan-mirror/ca.html#cem_PKCS1-1.5">EME-PKCS1-v1_5</a>
5685 class PKCS_EncryptionPaddingScheme : public PK_EncryptionMessageEncodingMethod
5687 public:
5688 static const char * StaticAlgorithmName() {return "EME-PKCS1-v1_5";}
5690 unsigned int MaxUnpaddedLength(unsigned int paddedLength) const;
5691 void Pad(RandomNumberGenerator &rng, const byte *raw, unsigned int inputLength, byte *padded, unsigned int paddedLength, const NameValuePairs &parameters) const;
5692 DecodingResult Unpad(const byte *padded, unsigned int paddedLength, byte *raw, const NameValuePairs &parameters) const;
5695 template <class H> class PKCS_DigestDecoration
5697 public:
5698 static const byte decoration[];
5699 static const unsigned int length;
5702 // PKCS_DigestDecoration can be instantiated with the following
5703 // classes as specified in PKCS#1 v2.0 and P1363a
5704 class SHA;
5705 // end of list
5707 //! <a href="http://www.weidai.com/scan-mirror/sig.html#sem_PKCS1-1.5">EMSA-PKCS1-v1_5</a>
5708 class CRYPTOPP_DLL PKCS1v15_SignatureMessageEncodingMethod : public PK_DeterministicSignatureMessageEncodingMethod
5710 public:
5711 static const char * StaticAlgorithmName() {return "EMSA-PKCS1-v1_5";}
5713 void ComputeMessageRepresentative(RandomNumberGenerator &rng,
5714 const byte *recoverableMessage, unsigned int recoverableMessageLength,
5715 HashTransformation &hash, HashIdentifier hashIdentifier, bool messageEmpty,
5716 byte *representative, unsigned int representativeBitLength) const;
5718 struct HashIdentifierLookup
5720 template <class H> struct HashIdentifierLookup2
5722 static HashIdentifier Lookup()
5724 return HashIdentifier(PKCS_DigestDecoration<H>::decoration, PKCS_DigestDecoration<H>::length);
5730 //! PKCS #1 version 1.5, for use with RSAES and RSASS
5731 /*! Only the following hash functions are supported by this signature standard:
5732 \dontinclude pkcspad.h
5733 \skip can be instantiated
5734 \until end of list
5736 struct PKCS1v15 : public SignatureStandard, public EncryptionStandard
5738 typedef PKCS_EncryptionPaddingScheme EncryptionMessageEncodingMethod;
5739 typedef PKCS1v15_SignatureMessageEncodingMethod SignatureMessageEncodingMethod;
5742 NAMESPACE_END
5744 #endif
5745 ////////////////////////////////////////////////////////////////////////////////
5749 ////////////////////////////////////////////////////////////////////////////////
5750 #ifndef CRYPTOPP_ASN_H
5751 #define CRYPTOPP_ASN_H
5753 //- #include "filters.h"
5754 //- #include "queue.h"
5755 #include <vector>
5757 NAMESPACE_BEGIN(CryptoPP)
5759 // these tags and flags are not complete
5760 enum ASNTag
5762 BOOLEAN = 0x01,
5763 INTEGER = 0x02,
5764 BIT_STRING = 0x03,
5765 OCTET_STRING = 0x04,
5766 TAG_NULL = 0x05,
5767 OBJECT_IDENTIFIER = 0x06,
5768 OBJECT_DESCRIPTOR = 0x07,
5769 EXTERNAL = 0x08,
5770 REAL = 0x09,
5771 ENUMERATED = 0x0a,
5772 UTF8_STRING = 0x0c,
5773 SEQUENCE = 0x10,
5774 SET = 0x11,
5775 NUMERIC_STRING = 0x12,
5776 PRINTABLE_STRING = 0x13,
5777 T61_STRING = 0x14,
5778 VIDEOTEXT_STRING = 0x15,
5779 IA5_STRING = 0x16,
5780 UTC_TIME = 0x17,
5781 GENERALIZED_TIME = 0x18,
5782 GRAPHIC_STRING = 0x19,
5783 VISIBLE_STRING = 0x1a,
5784 GENERAL_STRING = 0x1b
5787 enum ASNIdFlag
5789 UNIVERSAL = 0x00,
5790 // DATA = 0x01,
5791 // HEADER = 0x02,
5792 CONSTRUCTED = 0x20,
5793 APPLICATION = 0x40,
5794 CONTEXT_SPECIFIC = 0x80,
5795 PRIVATE = 0xc0
5798 inline void BERDecodeError() {throw BERDecodeErr();}
5800 // unsigned int DERLengthEncode(unsigned int length, byte *output=0);
5801 CRYPTOPP_DLL unsigned int DERLengthEncode(BufferedTransformation &out, unsigned int length);
5802 // returns false if indefinite length
5803 CRYPTOPP_DLL bool BERLengthDecode(BufferedTransformation &in, unsigned int &length);
5805 CRYPTOPP_DLL void DEREncodeNull(BufferedTransformation &out);
5806 CRYPTOPP_DLL void BERDecodeNull(BufferedTransformation &in);
5808 CRYPTOPP_DLL unsigned int DEREncodeOctetString(BufferedTransformation &out, const byte *str, unsigned int strLen);
5809 CRYPTOPP_DLL unsigned int DEREncodeOctetString(BufferedTransformation &out, const SecByteBlock &str);
5811 // BER decode from source and DER reencode into dest
5812 CRYPTOPP_DLL void DERReencode(BufferedTransformation &source, BufferedTransformation &dest);
5814 //! Object Identifier
5815 class CRYPTOPP_DLL OID
5817 public:
5818 OID() {}
5819 OID(unsigned long v) : m_values(1, v) {}
5820 OID(BufferedTransformation &bt) {BERDecode(bt);}
5822 inline OID & operator+=(unsigned long rhs) {m_values.push_back(rhs); return *this;}
5824 void DEREncode(BufferedTransformation &bt) const;
5825 void BERDecode(BufferedTransformation &bt);
5827 // throw BERDecodeErr() if decoded value doesn't equal this OID
5828 void BERDecodeAndCheck(BufferedTransformation &bt) const;
5830 std::vector<unsigned long> m_values;
5832 private:
5833 static void EncodeValue(BufferedTransformation &bt, unsigned long v);
5834 static unsigned int DecodeValue(BufferedTransformation &bt, unsigned long &v);
5837 //! BER General Decoder
5838 class CRYPTOPP_DLL BERGeneralDecoder : public Store
5840 public:
5841 explicit BERGeneralDecoder(BufferedTransformation &inQueue, byte asnTag);
5842 explicit BERGeneralDecoder(BERGeneralDecoder &inQueue, byte asnTag);
5843 ~BERGeneralDecoder();
5845 bool IsDefiniteLength() const {return m_definiteLength;}
5846 unsigned int RemainingLength() const {assert(m_definiteLength); return m_length;}
5847 bool EndReached() const;
5848 byte PeekByte() const;
5849 void CheckByte(byte b);
5851 unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
5852 unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const;
5854 // call this to denote end of sequence
5855 void MessageEnd();
5857 protected:
5858 BufferedTransformation &m_inQueue;
5859 bool m_finished, m_definiteLength;
5860 unsigned int m_length;
5862 private:
5863 void Init(byte asnTag);
5864 void StoreInitialize(const NameValuePairs& /* parameters */) {assert(false);}
5865 unsigned int ReduceLength(unsigned int delta);
5868 //! DER General Encoder
5869 class CRYPTOPP_DLL DERGeneralEncoder : public ByteQueue
5871 public:
5872 explicit DERGeneralEncoder(BufferedTransformation &outQueue, byte asnTag = SEQUENCE | CONSTRUCTED);
5873 explicit DERGeneralEncoder(DERGeneralEncoder &outQueue, byte asnTag = SEQUENCE | CONSTRUCTED);
5874 ~DERGeneralEncoder();
5876 // call this to denote end of sequence
5877 void MessageEnd();
5879 private:
5880 BufferedTransformation &m_outQueue;
5881 bool m_finished;
5883 byte m_asnTag;
5886 //! BER Sequence Decoder
5887 class CRYPTOPP_DLL BERSequenceDecoder : public BERGeneralDecoder
5889 public:
5890 explicit BERSequenceDecoder(BufferedTransformation &inQueue, byte asnTag = SEQUENCE | CONSTRUCTED)
5891 : BERGeneralDecoder(inQueue, asnTag) {}
5892 explicit BERSequenceDecoder(BERSequenceDecoder &inQueue, byte asnTag = SEQUENCE | CONSTRUCTED)
5893 : BERGeneralDecoder(inQueue, asnTag) {}
5896 //! DER Sequence Encoder
5897 class CRYPTOPP_DLL DERSequenceEncoder : public DERGeneralEncoder
5899 public:
5900 explicit DERSequenceEncoder(BufferedTransformation &outQueue, byte asnTag = SEQUENCE | CONSTRUCTED)
5901 : DERGeneralEncoder(outQueue, asnTag) {}
5902 explicit DERSequenceEncoder(DERSequenceEncoder &outQueue, byte asnTag = SEQUENCE | CONSTRUCTED)
5903 : DERGeneralEncoder(outQueue, asnTag) {}
5906 //! key that can be ASN.1 encoded
5907 /** derived class should override either BERDecodeKey or BERDecodeKey2 */
5908 class CRYPTOPP_DLL ASN1Key : public ASN1CryptoMaterial
5910 public:
5911 virtual OID GetAlgorithmID() const =0;
5912 virtual bool BERDecodeAlgorithmParameters(BufferedTransformation &bt)
5913 {BERDecodeNull(bt); return false;}
5914 virtual bool DEREncodeAlgorithmParameters(BufferedTransformation &bt) const
5915 {DEREncodeNull(bt); return false;} // see RFC 2459, section 7.3.1
5916 //! decode subjectPublicKey part of subjectPublicKeyInfo, or privateKey part of privateKeyInfo, without the BIT STRING or OCTET STRING header
5917 virtual void BERDecodeKey(BufferedTransformation& /* bt */) {assert(false);}
5918 virtual void BERDecodeKey2(BufferedTransformation& bt, bool /* parametersPresent */, unsigned int /* size */)
5919 {BERDecodeKey(bt);}
5920 //! encode subjectPublicKey part of subjectPublicKeyInfo, or privateKey part of privateKeyInfo, without the BIT STRING or OCTET STRING header
5921 virtual void DEREncodeKey(BufferedTransformation &bt) const =0;
5924 //! encodes/decodes subjectPublicKeyInfo
5925 class CRYPTOPP_DLL X509PublicKey : virtual public ASN1Key, public PublicKey
5927 public:
5928 void BERDecode(BufferedTransformation &bt);
5929 void DEREncode(BufferedTransformation &bt) const;
5932 //! encodes/decodes privateKeyInfo
5933 class CRYPTOPP_DLL PKCS8PrivateKey : virtual public ASN1Key, public PrivateKey
5935 public:
5936 void BERDecode(BufferedTransformation &bt);
5937 void DEREncode(BufferedTransformation &bt) const;
5939 //! decode optional attributes including context-specific tag
5940 /*! /note default implementation stores attributes to be output in DEREncodeOptionalAttributes */
5941 virtual void BERDecodeOptionalAttributes(BufferedTransformation &bt);
5942 //! encode optional attributes including context-specific tag
5943 virtual void DEREncodeOptionalAttributes(BufferedTransformation &bt) const;
5945 private:
5946 ByteQueue m_optionalAttributes;
5949 // ********************************************************
5951 //! DER Encode Unsigned
5952 /*! for INTEGER, BOOLEAN, and ENUM */
5953 template <class T>
5954 unsigned int DEREncodeUnsigned(BufferedTransformation &out, T w, byte asnTag = INTEGER)
5956 byte buf[sizeof(w)+1];
5957 unsigned int bc;
5958 if (asnTag == BOOLEAN)
5960 buf[sizeof(w)] = w ? 0xff : 0;
5961 bc = 1;
5963 else
5965 buf[0] = 0;
5966 for (unsigned int i=0; i<sizeof(w); i++)
5967 buf[i+1] = byte(w >> (sizeof(w)-1-i)*8);
5968 bc = sizeof(w);
5969 while (bc > 1 && buf[sizeof(w)+1-bc] == 0)
5970 --bc;
5971 if (buf[sizeof(w)+1-bc] & 0x80)
5972 ++bc;
5974 out.Put(asnTag);
5975 unsigned int lengthBytes = DERLengthEncode(out, bc);
5976 out.Put(buf+sizeof(w)+1-bc, bc);
5977 return 1+lengthBytes+bc;
5980 //! BER Decode Unsigned
5981 // VC60 workaround: std::numeric_limits<T>::max conflicts with MFC max macro
5982 // CW41 workaround: std::numeric_limits<T>::max causes a template error
5983 template <class T>
5984 void BERDecodeUnsigned(BufferedTransformation &in, T &w, byte asnTag = INTEGER,
5985 T minValue = 0, T maxValue = 0xffffffff)
5987 byte b;
5988 if (!in.Get(b) || b != asnTag)
5989 BERDecodeError();
5991 unsigned int bc;
5992 BERLengthDecode(in, bc);
5994 SecByteBlock buf(bc);
5996 if (bc != in.Get(buf, bc))
5997 BERDecodeError();
5999 const byte *ptr = buf;
6000 while (bc > sizeof(w) && *ptr == 0)
6002 bc--;
6003 ptr++;
6005 if (bc > sizeof(w))
6006 BERDecodeError();
6008 w = 0;
6009 for (unsigned int i=0; i<bc; i++)
6010 w = (w << 8) | ptr[i];
6012 if (w < minValue || w > maxValue)
6013 BERDecodeError();
6016 inline bool operator==(const ::CryptoPP::OID &lhs, const ::CryptoPP::OID &rhs)
6017 {return lhs.m_values == rhs.m_values;}
6018 inline bool operator!=(const ::CryptoPP::OID &lhs, const ::CryptoPP::OID &rhs)
6019 {return lhs.m_values != rhs.m_values;}
6020 inline bool operator<(const ::CryptoPP::OID &lhs, const ::CryptoPP::OID &rhs)
6021 {return std::lexicographical_compare(lhs.m_values.begin(), lhs.m_values.end(), rhs.m_values.begin(), rhs.m_values.end());}
6022 inline ::CryptoPP::OID operator+(const ::CryptoPP::OID &lhs, unsigned long rhs)
6023 {return ::CryptoPP::OID(lhs)+=rhs;}
6025 NAMESPACE_END
6027 #endif
6028 ////////////////////////////////////////////////////////////////////////////////
6032 ////////////////////////////////////////////////////////////////////////////////
6033 #ifndef CRYPTOPP_RSA_H
6034 #define CRYPTOPP_RSA_H
6036 /** \file
6037 This file contains classes that implement the RSA
6038 ciphers and signature schemes as defined in PKCS #1 v2.0.
6041 //- #include "pkcspad.h"
6042 //- #include "oaep.h"
6043 //- #include "integer.h"
6044 //- #include "asn.h"
6046 NAMESPACE_BEGIN(CryptoPP)
6048 //! _
6049 class CRYPTOPP_DLL RSAFunction : public TrapdoorFunction, public X509PublicKey
6051 typedef RSAFunction ThisClass;
6053 public:
6054 void Initialize(const Integer &n, const Integer &e)
6055 {m_n = n; m_e = e;}
6057 // X509PublicKey
6058 OID GetAlgorithmID() const;
6059 void BERDecodeKey(BufferedTransformation &bt);
6060 void DEREncodeKey(BufferedTransformation &bt) const;
6062 // CryptoMaterial
6063 bool Validate(RandomNumberGenerator &rng, unsigned int level) const;
6064 bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const;
6065 void AssignFrom(const NameValuePairs &source);
6067 // TrapdoorFunction
6068 Integer ApplyFunction(const Integer &x) const;
6069 Integer PreimageBound() const {return m_n;}
6070 Integer ImageBound() const {return m_n;}
6072 // non-derived
6073 const Integer & GetModulus() const {return m_n;}
6074 const Integer & GetPublicExponent() const {return m_e;}
6076 void SetModulus(const Integer &n) {m_n = n;}
6077 void SetPublicExponent(const Integer &e) {m_e = e;}
6079 protected:
6080 Integer m_n, m_e;
6083 //! _
6084 class CRYPTOPP_DLL InvertibleRSAFunction : public RSAFunction, public TrapdoorFunctionInverse, public PKCS8PrivateKey
6086 typedef InvertibleRSAFunction ThisClass;
6088 public:
6089 void Initialize(RandomNumberGenerator &rng, unsigned int modulusBits, const Integer &e = 17);
6090 void Initialize(const Integer &n, const Integer &e, const Integer &d, const Integer &p, const Integer &q, const Integer &dp, const Integer &dq, const Integer &u)
6091 {m_n = n; m_e = e; m_d = d; m_p = p; m_q = q; m_dp = dp; m_dq = dq; m_u = u;}
6092 //! factor n given private exponent
6093 void Initialize(const Integer &n, const Integer &e, const Integer &d);
6095 // PKCS8PrivateKey
6096 void BERDecode(BufferedTransformation &bt)
6097 {PKCS8PrivateKey::BERDecode(bt);}
6098 void DEREncode(BufferedTransformation &bt) const
6099 {PKCS8PrivateKey::DEREncode(bt);}
6100 void BERDecodeKey(BufferedTransformation &bt);
6101 void DEREncodeKey(BufferedTransformation &bt) const;
6103 // TrapdoorFunctionInverse
6104 Integer CalculateInverse(RandomNumberGenerator &rng, const Integer &x) const;
6106 // GeneratableCryptoMaterial
6107 bool Validate(RandomNumberGenerator &rng, unsigned int level) const;
6108 /*! parameters: (ModulusSize, PublicExponent (default 17)) */
6109 void GenerateRandom(RandomNumberGenerator &rng, const NameValuePairs &alg);
6110 bool GetVoidValue(const char *name, const std::type_info &valueType, void *pValue) const;
6111 void AssignFrom(const NameValuePairs &source);
6113 // non-derived interface
6114 const Integer& GetPrime1() const {return m_p;}
6115 const Integer& GetPrime2() const {return m_q;}
6116 const Integer& GetPrivateExponent() const {return m_d;}
6117 const Integer& GetModPrime1PrivateExponent() const {return m_dp;}
6118 const Integer& GetModPrime2PrivateExponent() const {return m_dq;}
6119 const Integer& GetMultiplicativeInverseOfPrime2ModPrime1() const {return m_u;}
6121 void SetPrime1(const Integer &p) {m_p = p;}
6122 void SetPrime2(const Integer &q) {m_q = q;}
6123 void SetPrivateExponent(const Integer &d) {m_d = d;}
6124 void SetModPrime1PrivateExponent(const Integer &dp) {m_dp = dp;}
6125 void SetModPrime2PrivateExponent(const Integer &dq) {m_dq = dq;}
6126 void SetMultiplicativeInverseOfPrime2ModPrime1(const Integer &u) {m_u = u;}
6128 protected:
6129 Integer m_d, m_p, m_q, m_dp, m_dq, m_u;
6132 //! RSA
6133 struct CRYPTOPP_DLL RSA
6135 static std::string StaticAlgorithmName() {return "RSA";}
6136 typedef RSAFunction PublicKey;
6137 typedef InvertibleRSAFunction PrivateKey;
6140 //! <a href="http://www.weidai.com/scan-mirror/sig.html#RSA">RSA signature scheme with appendix</a>
6141 /*! See documentation of PKCS1v15 for a list of hash functions that can be used with it. */
6142 template <class STANDARD, class H>
6143 struct RSASS : public TF_SS<STANDARD, H, RSA>
6147 // The three RSA signature schemes defined in PKCS #1 v2.0
6148 typedef RSASS<PKCS1v15, SHA>::Signer RSASSA_PKCS1v15_SHA_Signer;
6149 typedef RSASS<PKCS1v15, SHA>::Verifier RSASSA_PKCS1v15_SHA_Verifier;
6151 NAMESPACE_END
6153 #endif
6154 ////////////////////////////////////////////////////////////////////////////////
6158 ////////////////////////////////////////////////////////////////////////////////
6159 #ifndef CRYPTOPP_BASECODE_H
6160 #define CRYPTOPP_BASECODE_H
6162 //- #include "filters.h"
6163 //- #include "algparam.h"
6164 //- #include "argnames.h"
6166 NAMESPACE_BEGIN(CryptoPP)
6168 //! base n encoder, where n is a power of 2
6169 class CRYPTOPP_DLL BaseN_Encoder : public Unflushable<Filter>
6171 public:
6172 BaseN_Encoder(BufferedTransformation *attachment=NULL)
6173 {Detach(attachment);}
6175 BaseN_Encoder(const byte *alphabet, int log2base, BufferedTransformation *attachment=NULL, int padding=-1)
6177 Detach(attachment);
6178 IsolatedInitialize(MakeParameters(Name::EncodingLookupArray(), alphabet)
6179 (Name::Log2Base(), log2base)
6180 (Name::Pad(), padding != -1)
6181 (Name::PaddingByte(), byte(padding)));
6184 void IsolatedInitialize(const NameValuePairs &parameters);
6185 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking);
6187 private:
6188 const byte *m_alphabet;
6189 int m_padding, m_bitsPerChar, m_outputBlockSize;
6190 int m_bytePos, m_bitPos;
6191 SecByteBlock m_outBuf;
6194 //! base n decoder, where n is a power of 2
6195 class CRYPTOPP_DLL BaseN_Decoder : public Unflushable<Filter>
6197 public:
6198 BaseN_Decoder(BufferedTransformation *attachment=NULL)
6199 {Detach(attachment);}
6201 BaseN_Decoder(const int *lookup, int log2base, BufferedTransformation *attachment=NULL)
6203 Detach(attachment);
6204 IsolatedInitialize(MakeParameters(Name::DecodingLookupArray(), lookup)(Name::Log2Base(), log2base));
6207 void IsolatedInitialize(const NameValuePairs &parameters);
6208 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking);
6210 static void InitializeDecodingLookupArray(int *lookup, const byte *alphabet, unsigned int base, bool caseInsensitive);
6212 private:
6213 const int *m_lookup;
6214 int m_padding, m_bitsPerChar, m_outputBlockSize;
6215 int m_bytePos, m_bitPos;
6216 SecByteBlock m_outBuf;
6219 //! filter that breaks input stream into groups of fixed size
6220 class CRYPTOPP_DLL Grouper : public Bufferless<Filter>
6222 public:
6223 Grouper(BufferedTransformation *attachment=NULL)
6224 {Detach(attachment);}
6226 Grouper(int groupSize, const std::string &separator, const std::string &terminator, BufferedTransformation *attachment=NULL)
6228 Detach(attachment);
6229 IsolatedInitialize(MakeParameters(Name::GroupSize(), groupSize)
6230 (Name::Separator(), ConstByteArrayParameter(separator))
6231 (Name::Terminator(), ConstByteArrayParameter(terminator)));
6234 void IsolatedInitialize(const NameValuePairs &parameters);
6235 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking);
6237 private:
6238 SecByteBlock m_separator, m_terminator;
6239 unsigned int m_groupSize, m_counter;
6242 NAMESPACE_END
6244 #endif
6245 ////////////////////////////////////////////////////////////////////////////////
6249 ////////////////////////////////////////////////////////////////////////////////
6250 #ifndef CRYPTOPP_BASE64_H
6251 #define CRYPTOPP_BASE64_H
6253 //- #include "basecode.h"
6255 NAMESPACE_BEGIN(CryptoPP)
6257 //! Base64 Encoder Class
6258 class Base64Encoder : public SimpleProxyFilter
6260 public:
6261 Base64Encoder(BufferedTransformation *attachment = NULL, bool insertLineBreaks = true, int maxLineLength = 72)
6262 : SimpleProxyFilter(new BaseN_Encoder(new Grouper), attachment)
6264 IsolatedInitialize(MakeParameters(Name::InsertLineBreaks(), insertLineBreaks)(Name::MaxLineLength(), maxLineLength));
6267 void IsolatedInitialize(const NameValuePairs &parameters);
6270 //! Base64 Decoder Class
6271 class Base64Decoder : public BaseN_Decoder
6273 public:
6274 Base64Decoder(BufferedTransformation *attachment = NULL)
6275 : BaseN_Decoder(GetDecodingLookupArray(), 6, attachment) {}
6277 void IsolatedInitialize(const NameValuePairs& /* parameters */) {}
6279 private:
6280 static const int *GetDecodingLookupArray();
6283 NAMESPACE_END
6285 #endif
6286 ////////////////////////////////////////////////////////////////////////////////
6290 ////////////////////////////////////////////////////////////////////////////////
6291 #ifndef CRYPTOPP_FILES_H
6292 #define CRYPTOPP_FILES_H
6294 //- #include "cryptlib.h"
6295 //- #include "filters.h"
6296 //- #include "argnames.h"
6298 #include <iostream>
6299 #include <fstream>
6301 NAMESPACE_BEGIN(CryptoPP)
6303 //! file-based implementation of Store interface
6304 class CRYPTOPP_DLL FileStore : public Store, private FilterPutSpaceHelper, public NotCopyable
6306 public:
6307 class Err : public Exception
6309 public:
6310 Err(const std::string &s) : Exception(IO_ERROR, s) {}
6312 class OpenErr : public Err {public: OpenErr(const std::string &filename) : Err("FileStore: error opening file for reading: " + filename) {}};
6313 class ReadErr : public Err {public: ReadErr() : Err("FileStore: error reading file") {}};
6315 FileStore() : m_stream(NULL) {}
6316 FileStore(std::istream &in)
6317 {StoreInitialize(MakeParameters(Name::InputStreamPointer(), &in));}
6318 FileStore(const char *filename)
6319 {StoreInitialize(MakeParameters(Name::InputFileName(), filename));}
6321 std::istream* GetStream() {return m_stream;}
6323 unsigned long MaxRetrievable() const;
6324 unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
6325 unsigned int CopyRangeTo2(BufferedTransformation &target, unsigned long &begin, unsigned long end=ULONG_MAX, const std::string &channel=NULL_CHANNEL, bool blocking=true) const;
6326 unsigned long Skip(unsigned long skipMax=ULONG_MAX);
6328 private:
6329 void StoreInitialize(const NameValuePairs &parameters);
6331 member_ptr<std::ifstream> m_file;
6332 std::istream *m_stream;
6333 byte *m_space;
6334 unsigned int m_len;
6335 bool m_waiting;
6338 //! file-based implementation of Source interface
6339 class CRYPTOPP_DLL FileSource : public SourceTemplate<FileStore>
6341 public:
6342 typedef FileStore::Err Err;
6343 typedef FileStore::OpenErr OpenErr;
6344 typedef FileStore::ReadErr ReadErr;
6346 FileSource(BufferedTransformation *attachment = NULL)
6347 : SourceTemplate<FileStore>(attachment) {}
6348 FileSource(std::istream &in, bool pumpAll, BufferedTransformation *attachment = NULL)
6349 : SourceTemplate<FileStore>(attachment) {SourceInitialize(pumpAll, MakeParameters(Name::InputStreamPointer(), &in));}
6350 FileSource(const char *filename, bool pumpAll, BufferedTransformation *attachment = NULL, bool binary=true)
6351 : SourceTemplate<FileStore>(attachment) {SourceInitialize(pumpAll, MakeParameters(Name::InputFileName(), filename)(Name::InputBinaryMode(), binary));}
6353 std::istream* GetStream() {return m_store.GetStream();}
6356 //! file-based implementation of Sink interface
6357 class CRYPTOPP_DLL FileSink : public Sink, public NotCopyable
6359 public:
6360 class Err : public Exception
6362 public:
6363 Err(const std::string &s) : Exception(IO_ERROR, s) {}
6365 class OpenErr : public Err {public: OpenErr(const std::string &filename) : Err("FileSink: error opening file for writing: " + filename) {}};
6366 class WriteErr : public Err {public: WriteErr() : Err("FileSink: error writing file") {}};
6368 FileSink() : m_stream(NULL) {}
6369 FileSink(std::ostream &out)
6370 {IsolatedInitialize(MakeParameters(Name::OutputStreamPointer(), &out));}
6371 FileSink(const char *filename, bool binary=true)
6372 {IsolatedInitialize(MakeParameters(Name::OutputFileName(), filename)("OutputBinaryMode", binary));}
6374 std::ostream* GetStream() {return m_stream;}
6376 void IsolatedInitialize(const NameValuePairs &parameters);
6377 unsigned int Put2(const byte *inString, unsigned int length, int messageEnd, bool blocking);
6378 bool IsolatedFlush(bool hardFlush, bool blocking);
6380 private:
6381 member_ptr<std::ofstream> m_file;
6382 std::ostream *m_stream;
6385 NAMESPACE_END
6387 #endif
6388 ////////////////////////////////////////////////////////////////////////////////
6392 ////////////////////////////////////////////////////////////////////////////////
6393 #ifndef CRYPTOPP_RANDPOOL_H
6394 #define CRYPTOPP_RANDPOOL_H
6396 //- #include "cryptlib.h"
6397 //- #include "filters.h"
6399 NAMESPACE_BEGIN(CryptoPP)
6401 //! Randomness Pool
6402 /*! This class can be used to generate
6403 pseudorandom bytes after seeding the pool with
6404 the Put() methods */
6405 class CRYPTOPP_DLL RandomPool : public RandomNumberGenerator,
6406 public Bufferless<BufferedTransformation>
6408 public:
6409 //! poolSize must be greater than 16
6410 RandomPool(unsigned int poolSize=384);
6412 unsigned int Put2(const byte *begin, unsigned int, int messageEnd, bool blocking);
6414 bool AnyRetrievable() const {return true;}
6415 unsigned long MaxRetrievable() const {return ULONG_MAX;}
6417 unsigned int TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel=NULL_CHANNEL, bool blocking=true);
6418 unsigned int CopyRangeTo2(BufferedTransformation& /* target */, unsigned long& /* begin */, unsigned long /* end */ = ULONG_MAX, const std::string& /* channel */ = NULL_CHANNEL, bool /* blocking */ = true) const
6420 throw NotImplemented("RandomPool: CopyRangeTo2() is not supported by this store");
6423 byte GenerateByte();
6424 void GenerateBlock(byte *output, unsigned int size);
6426 void IsolatedInitialize(const NameValuePairs& /* parameters */) {}
6428 protected:
6429 void Stir();
6431 private:
6432 SecByteBlock pool, key;
6433 unsigned int addPos, getPos;
6436 NAMESPACE_END
6438 #endif
6439 ////////////////////////////////////////////////////////////////////////////////
6443 ////////////////////////////////////////////////////////////////////////////////
6444 // seckey.h - written and placed in the public domain by Wei Dai
6446 // This file contains helper classes/functions for implementing secret key algorithms.
6448 #ifndef CRYPTOPP_SECKEY_H
6449 #define CRYPTOPP_SECKEY_H
6451 //- #include "cryptlib.h"
6452 //- #include "misc.h"
6453 //- #include "simple.h"
6455 NAMESPACE_BEGIN(CryptoPP)
6457 //! to be inherited by block ciphers with fixed block size
6458 template <unsigned int N>
6459 class FixedBlockSize
6461 public:
6462 enum {BLOCKSIZE = N};
6465 // ************** key length ***************
6467 //! to be inherited by keyed algorithms with fixed key length
6468 template <unsigned int N, unsigned int IV_REQ = SimpleKeyingInterface::NOT_RESYNCHRONIZABLE>
6469 class FixedKeyLength
6471 public:
6472 enum {KEYLENGTH=N, MIN_KEYLENGTH=N, MAX_KEYLENGTH=N, DEFAULT_KEYLENGTH=N};
6473 enum {IV_REQUIREMENT = IV_REQ};
6474 static unsigned int StaticGetValidKeyLength(unsigned int) {return KEYLENGTH;}
6477 // ************** implementation helper for SimpledKeyed ***************
6479 template <class T>
6480 static inline void CheckedSetKey(T *obj, Empty empty, const byte *key, unsigned int length, const NameValuePairs &param)
6482 obj->ThrowIfInvalidKeyLength(length);
6483 obj->UncheckedSetKey(key, length);
6486 template <class T>
6487 static inline void CheckedSetKey(T *obj, CipherDir dir, const byte *key, unsigned int length, const NameValuePairs& /* param */)
6489 obj->ThrowIfInvalidKeyLength(length);
6490 obj->UncheckedSetKey(dir, key, length);
6493 //! _
6494 template <class BASE, class INFO = BASE>
6495 class CRYPTOPP_NO_VTABLE SimpleKeyingInterfaceImpl : public BASE
6497 public:
6498 unsigned int MinKeyLength() const {return INFO::MIN_KEYLENGTH;}
6499 unsigned int MaxKeyLength() const {return (unsigned int)INFO::MAX_KEYLENGTH;}
6500 unsigned int DefaultKeyLength() const {return INFO::DEFAULT_KEYLENGTH;}
6501 unsigned int GetValidKeyLength(unsigned int n) const {return INFO::StaticGetValidKeyLength(n);}
6502 typename BASE::IV_Requirement IVRequirement() const {return (typename BASE::IV_Requirement)INFO::IV_REQUIREMENT;}
6504 protected:
6505 void AssertValidKeyLength(unsigned int length) {assert(GetValidKeyLength(length) == length);}
6508 template <class INFO, class BASE = BlockCipher>
6509 class CRYPTOPP_NO_VTABLE BlockCipherImpl : public AlgorithmImpl<SimpleKeyingInterfaceImpl<TwoBases<BASE, INFO> > >
6511 public:
6512 unsigned int BlockSize() const {return this->BLOCKSIZE;}
6515 //! _
6516 template <CipherDir DIR, class BASE>
6517 class BlockCipherFinal : public ClonableImpl<BlockCipherFinal<DIR, BASE>, BASE>
6519 public:
6520 BlockCipherFinal() {}
6521 BlockCipherFinal(const byte *key)
6522 {SetKey(key, this->DEFAULT_KEYLENGTH);}
6523 BlockCipherFinal(const byte *key, unsigned int length)
6524 {SetKey(key, length);}
6525 BlockCipherFinal(const byte *key, unsigned int length, unsigned int rounds)
6526 {this->SetKeyWithRounds(key, length, rounds);}
6528 bool IsForwardTransformation() const {return DIR == ENCRYPTION;}
6530 void SetKey(const byte *key, unsigned int length, const NameValuePairs &param = g_nullNameValuePairs)
6532 CheckedSetKey(this, DIR, key, length, param);
6536 // ************** documentation ***************
6538 /*! \brief Each class derived from this one defines two types, Encryption and Decryption,
6539 both of which implement the SymmetricCipher interface. Two types of classes derive
6540 from this class: stream ciphers and block cipher modes. Stream ciphers can be used
6541 alone, cipher mode classes need to be used with a block cipher. See CipherModeDocumentation
6542 for more for information about using cipher modes and block ciphers. */
6543 struct SymmetricCipherDocumentation
6545 //! implements the SymmetricCipher interface
6546 typedef SymmetricCipher Encryption;
6547 //! implements the SymmetricCipher interface
6548 typedef SymmetricCipher Decryption;
6551 NAMESPACE_END
6553 #endif
6554 ////////////////////////////////////////////////////////////////////////////////
6558 ////////////////////////////////////////////////////////////////////////////////
6559 #ifndef CRYPTOPP_OSRNG_H
6560 #define CRYPTOPP_OSRNG_H
6562 //- #include "config.h"
6564 #ifdef OS_RNG_AVAILABLE
6566 //- #include "randpool.h"
6567 //- #include "rng.h"
6568 //- #include "des.h"
6569 //- #include "fips140.h"
6571 NAMESPACE_BEGIN(CryptoPP)
6573 //! Exception class for Operating-System Random Number Generator.
6574 class CRYPTOPP_DLL OS_RNG_Err : public Exception
6576 public:
6577 OS_RNG_Err(const std::string &operation);
6580 #ifdef NONBLOCKING_RNG_AVAILABLE
6582 #ifdef CRYPTOPP_WIN32_AVAILABLE
6583 class CRYPTOPP_DLL MicrosoftCryptoProvider
6585 public:
6586 MicrosoftCryptoProvider();
6587 ~MicrosoftCryptoProvider();
6588 #if defined(_WIN64)
6589 typedef unsigned __int64 ProviderHandle; // type HCRYPTPROV, avoid #include <windows.h>
6590 #else
6591 typedef unsigned long ProviderHandle;
6592 #endif
6593 ProviderHandle GetProviderHandle() const {return m_hProvider;}
6594 private:
6595 ProviderHandle m_hProvider;
6598 #pragma comment(lib, "advapi32.lib")
6599 #endif
6601 //! encapsulate CryptoAPI's CryptGenRandom or /dev/urandom
6602 class CRYPTOPP_DLL NonblockingRng : public RandomNumberGenerator
6604 public:
6605 NonblockingRng();
6606 ~NonblockingRng();
6607 byte GenerateByte();
6608 void GenerateBlock(byte *output, unsigned int size);
6610 protected:
6611 #ifdef CRYPTOPP_WIN32_AVAILABLE
6612 # ifndef WORKAROUND_MS_BUG_Q258000
6613 MicrosoftCryptoProvider m_Provider;
6614 # endif
6615 #else
6616 int m_fd;
6617 #endif
6620 #endif
6622 #ifdef BLOCKING_RNG_AVAILABLE
6624 //! encapsulate /dev/random
6625 class CRYPTOPP_DLL BlockingRng : public RandomNumberGenerator
6627 public:
6628 BlockingRng();
6629 ~BlockingRng();
6630 byte GenerateByte();
6631 void GenerateBlock(byte *output, unsigned int size);
6633 protected:
6634 int m_fd;
6637 #endif
6639 CRYPTOPP_DLL void OS_GenerateRandomBlock(bool blocking, byte *output, unsigned int size);
6641 //! Automaticly Seeded Randomness Pool
6642 /*! This class seeds itself using an operating system provided RNG. */
6643 class CRYPTOPP_DLL AutoSeededRandomPool : public RandomPool
6645 public:
6646 //! blocking will be ignored if the preferred RNG isn't available
6647 explicit AutoSeededRandomPool(bool blocking = false, unsigned int seedSize = 32)
6648 {Reseed(blocking, seedSize);}
6649 void Reseed(bool blocking = false, unsigned int seedSize = 32);
6652 NAMESPACE_END
6654 #endif
6656 #endif
6657 ////////////////////////////////////////////////////////////////////////////////
6661 ////////////////////////////////////////////////////////////////////////////////
6662 #ifndef CRYPTOPP_MD4_H
6663 #define CRYPTOPP_MD4_H
6665 //- #include "iterhash.h"
6667 NAMESPACE_BEGIN(CryptoPP)
6669 //! <a href="http://www.weidai.com/scan-mirror/md.html#MD4">MD4</a>
6670 /*! \warning MD4 is considered insecure, and should not be used
6671 unless you absolutely need compatibility with a broken product. */
6672 class MD4 : public IteratedHashWithStaticTransform<word32, LittleEndian, 64, 16, MD4>
6674 public:
6675 static void InitState(HashWordType *state);
6676 static void Transform(word32 *digest, const word32 *data);
6677 static const char *StaticAlgorithmName() {return "MD4";}
6680 NAMESPACE_END
6682 #endif
6683 ////////////////////////////////////////////////////////////////////////////////
6685 #endif