diff options
author | weidai <weidai@57ff6487-cd31-0410-9ec3-f628ee90f5f0> | 2003-03-20 01:24:12 +0000 |
---|---|---|
committer | weidai <weidai@57ff6487-cd31-0410-9ec3-f628ee90f5f0> | 2003-03-20 01:24:12 +0000 |
commit | d23a489940499bd6c634a1cb0a9875f094f8a850 (patch) | |
tree | f85b3bed971083e90e5f3dbb84539ea4ba0359e9 /pssr.h | |
parent | b3517523a738277cfe22428bd757833e69abb66e (diff) | |
download | cryptopp-d23a489940499bd6c634a1cb0a9875f094f8a850.tar.gz |
various changes for 5.1
git-svn-id: svn://svn.code.sf.net/p/cryptopp/code/trunk/c5@38 57ff6487-cd31-0410-9ec3-f628ee90f5f0
Diffstat (limited to 'pssr.h')
-rw-r--r-- | pssr.h | 199 |
1 files changed, 58 insertions, 141 deletions
@@ -6,163 +6,80 @@ NAMESPACE_BEGIN(CryptoPP) -// TODO: implement standard variant of PSSR -template <class H, class MGF=P1363_MGF1<H> > -class PSSR : public SignatureEncodingMethodWithRecovery +class PSSR_MEM_Base : public PK_RecoverableSignatureMessageEncodingMethod { -public: - PSSR(unsigned int representativeBitLen); - PSSR(const byte *representative, unsigned int representativeBitLen); - ~PSSR() {} - void Update(const byte *input, unsigned int length); - unsigned int DigestSize() const {return BitsToBytes(representativeBitLen);} - void Restart() {h.Restart();} - void Encode(RandomNumberGenerator &rng, byte *representative); - bool Verify(const byte *representative); - DecodingResult Decode(byte *message); - unsigned int MaximumRecoverableLength() const {return MaximumRecoverableLength(representativeBitLen);} - static unsigned int MaximumRecoverableLength(unsigned int representativeBitLen); - static bool AllowLeftoverMessage() {return true;} - -protected: - static void EncodeRepresentative(byte *representative, unsigned int representativeBitLen, const byte *w, const byte *seed, const byte *m1, unsigned int m1Len); - static unsigned int DecodeRepresentative(const byte *representative, unsigned int representativeBitLen, byte *w, byte *seed, byte *m1); + virtual bool AllowRecovery() const =0; + virtual unsigned int SaltLen(unsigned int hashLen) const =0; + virtual unsigned int MinPadLen(unsigned int hashLen) const =0; + virtual const MaskGeneratingFunction & GetMGF() const =0; - unsigned int representativeBitLen, m1Len; - H h; - SecByteBlock m1, w, seed; +public: + unsigned int MaxRecoverableLength(unsigned int representativeBitLength, unsigned int hashIdentifierLength, unsigned int digestLength) const; + bool IsProbabilistic() const; + bool AllowNonrecoverablePart() const; + bool RecoverablePartFirst() const; + void ComputeMessageRepresentative(RandomNumberGenerator &rng, + const byte *recoverableMessage, unsigned int recoverableMessageLength, + HashTransformation &hash, HashIdentifier hashIdentifier, bool messageEmpty, + byte *representative, unsigned int representativeBitLength) const; + DecodingResult RecoverMessageFromRepresentative( + HashTransformation &hash, HashIdentifier hashIdentifier, bool messageEmpty, + byte *representative, unsigned int representativeBitLength, + byte *recoverableMessage) const; }; -template <class H, class MGF> -PSSR<H,MGF>::PSSR(unsigned int representativeBitLen) - : representativeBitLen(representativeBitLen), m1Len(0) - , m1(MaximumRecoverableLength()), w(H::DIGESTSIZE), seed(H::DIGESTSIZE) -{ -} - -template <class H, class MGF> -PSSR<H,MGF>::PSSR(const byte *representative, unsigned int representativeBitLen) - : representativeBitLen(representativeBitLen), m1Len(0) - , m1(MaximumRecoverableLength()), w(H::DIGESTSIZE), seed(H::DIGESTSIZE) -{ - m1Len = DecodeRepresentative(representative, representativeBitLen, w, seed, m1); - h.Update(m1, m1Len); -} - -template <class H, class MGF> -void PSSR<H,MGF>::Update(const byte *input, unsigned int length) +template <class H> struct EMSA2HashId { - unsigned int m1LenInc = STDMIN(length, MaximumRecoverableLength() - m1Len); - memcpy(m1+m1Len, input, m1LenInc); - m1Len += m1LenInc; - h.Update(input, length); -} - -template <class H, class MGF> -void PSSR<H,MGF>::Encode(RandomNumberGenerator &rng, byte *representative) -{ - rng.GenerateBlock(seed, seed.size()); - h.Update(seed, seed.size()); - h.Final(w); - EncodeRepresentative(representative, representativeBitLen, w, seed, m1, m1Len); -} + static const byte id; +}; -template <class H, class MGF> -bool PSSR<H,MGF>::Verify(const byte *representative) -{ - SecByteBlock m1r(MaximumRecoverableLength()), wr(H::DIGESTSIZE); - unsigned int m1rLen = DecodeRepresentative(representative, representativeBitLen, wr, seed, m1r); - h.Update(seed, seed.size()); - h.Final(w); - return m1Len==m1rLen && memcmp(m1, m1r, m1Len)==0 && w==wr; -} +// EMSA2HashId can be instantiated with the following two classes. +class SHA; +class RIPEMD160; -template <class H, class MGF> -DecodingResult PSSR<H,MGF>::Decode(byte *message) +template <class BASE> +class EMSA2HashIdLookup : public BASE { - SecByteBlock wh(H::DIGESTSIZE); - h.Update(seed, seed.size()); - h.Final(wh); - if (wh == w) +public: + struct HashIdentifierLookup { - memcpy(message, m1, m1Len); - return DecodingResult(m1Len); - } - else - return DecodingResult(); -} + template <class H> struct HashIdentifierLookup2 + { + static HashIdentifier Lookup() + { + return HashIdentifier(&EMSA2HashId<H>::id, 1); + } + }; + }; +}; -template <class H, class MGF> -unsigned int PSSR<H,MGF>::MaximumRecoverableLength(unsigned int paddedLength) -{ - return paddedLength/8 > 1+2*H::DIGESTSIZE ? paddedLength/8-1-2*H::DIGESTSIZE : 0; -} +template <bool USE_HASH_ID> class PSSR_MEM_BaseWithHashId; +template<> class PSSR_MEM_BaseWithHashId<true> : public EMSA2HashIdLookup<PSSR_MEM_Base> {}; +template<> class PSSR_MEM_BaseWithHashId<false> : public PSSR_MEM_Base {}; -template <class H, class MGF> -void PSSR<H,MGF>::EncodeRepresentative(byte *pssrBlock, unsigned int pssrBlockLen, const byte *w, const byte *seed, const byte *m1, unsigned int m1Len) +template <bool ALLOW_RECOVERY, class MGF=P1363_MGF1, int SALT_LEN=-1, int MIN_PAD_LEN=0, bool USE_HASH_ID=false> +class PSSR_MEM : public PSSR_MEM_BaseWithHashId<USE_HASH_ID> { - assert (m1Len <= MaximumRecoverableLength(pssrBlockLen)); - - // convert from bit length to byte length - if (pssrBlockLen % 8 != 0) - { - pssrBlock[0] = 0; - pssrBlock++; - } - pssrBlockLen /= 8; - - const unsigned int hLen = H::DIGESTSIZE; - const unsigned int wLen = hLen, seedLen = hLen, dbLen = pssrBlockLen-wLen-seedLen; - byte *const maskedSeed = pssrBlock+wLen; - byte *const maskedDB = pssrBlock+wLen+seedLen; + virtual bool AllowRecovery() const {return ALLOW_RECOVERY;} + virtual unsigned int SaltLen(unsigned int hashLen) const {return SALT_LEN < 0 ? hashLen : SALT_LEN;} + virtual unsigned int MinPadLen(unsigned int hashLen) const {return MIN_PAD_LEN < 0 ? hashLen : MIN_PAD_LEN;} + virtual const MaskGeneratingFunction & GetMGF() const {static MGF mgf; return mgf;} - memcpy(pssrBlock, w, wLen); - memcpy(maskedSeed, seed, seedLen); - memset(maskedDB, 0, dbLen-m1Len-1); - maskedDB[dbLen-m1Len-1] = 0x01; - memcpy(maskedDB+dbLen-m1Len, m1, m1Len); - - MGF::GenerateAndMask(maskedSeed, seedLen+dbLen, w, wLen); -} +public: + static std::string StaticAlgorithmName() {return std::string(ALLOW_RECOVERY ? "PSSR-" : "PSS-") + MGF::StaticAlgorithmName();} +}; -template <class H, class MGF> -unsigned int PSSR<H,MGF>::DecodeRepresentative(const byte *pssrBlock, unsigned int pssrBlockLen, byte *w, byte *seed, byte *m1) +//! <a href="http://www.weidai.com/scan-mirror/sig.html#sem_PSSR-MGF1">PSSR-MGF1</a> +struct PSSR : public SignatureStandard { - // convert from bit length to byte length - if (pssrBlockLen % 8 != 0) - { - if (pssrBlock[0] != 0) - return 0; - pssrBlock++; - } - pssrBlockLen /= 8; - - const unsigned int hLen = H::DIGESTSIZE; - const unsigned int wLen = hLen, seedLen = hLen, dbLen = pssrBlockLen-wLen-seedLen; - - if (pssrBlockLen < 2*hLen+1) - return 0; - - memcpy(w, pssrBlock, wLen); - SecByteBlock t(pssrBlock+wLen, pssrBlockLen-wLen); - byte *const maskedSeed = t; - byte *const maskedDB = t+seedLen; - - MGF::GenerateAndMask(maskedSeed, seedLen+dbLen, w, wLen); - memcpy(seed, maskedSeed, seedLen); - - // DB = 00 ... || 01 || M + typedef PSSR_MEM<true> SignatureMessageEncodingMethod; +}; - byte *M = std::find_if(maskedDB, maskedDB+dbLen, std::bind2nd(std::not_equal_to<byte>(), 0)); - if (M!=maskedDB+dbLen && *M == 0x01) - { - M++; - memcpy(m1, M, maskedDB+dbLen-M); - return maskedDB+dbLen-M; - } - else - return 0; -} +//! <a href="http://www.weidai.com/scan-mirror/sig.html#sem_PSS-MGF1">PSS-MGF1</a> +struct PSS : public SignatureStandard +{ + typedef PSSR_MEM<false> SignatureMessageEncodingMethod; +}; NAMESPACE_END |