Crypto++ 7.0 Free C++ class library of cryptographic schemes

authenc.cpp
1 // authenc.cpp - originally written and placed in the public domain by Wei Dai
2
3 #include "pch.h"
4
5 #ifndef CRYPTOPP_IMPORTS
6
7 #include "authenc.h"
8
9 NAMESPACE_BEGIN(CryptoPP)
10
11 void AuthenticatedSymmetricCipherBase::AuthenticateData(const byte *input, size_t len)
12 {
13 unsigned int blockSize = AuthenticationBlockSize();
14 unsigned int &num = m_bufferedDataLength;
15 byte* data = m_buffer.begin();
16
17 if (num != 0) // process left over data
18 {
19 if (num+len >= blockSize)
20 {
21 memcpy(data+num, input, blockSize-num);
22 AuthenticateBlocks(data, blockSize);
23 input += (blockSize-num);
24 len -= (blockSize-num);
25 num = 0;
26 // drop through and do the rest
27 }
28 else
29 {
30 memcpy(data+num, input, len);
31 num += (unsigned int)len;
32 return;
33 }
34 }
35
36 // now process the input data in blocks of blockSize bytes and save the leftovers to m_data
37 if (len >= blockSize)
38 {
39 size_t leftOver = AuthenticateBlocks(input, len);
40 input += (len - leftOver);
41 len = leftOver;
42 }
43
44 memcpy(data, input, len);
45 num = (unsigned int)len;
46 }
47
48 void AuthenticatedSymmetricCipherBase::SetKey(const byte *userKey, size_t keylength, const NameValuePairs &params)
49 {
50 m_bufferedDataLength = 0;
51 m_state = State_Start;
52
53 this->SetKeyWithoutResync(userKey, keylength, params);
54 m_state = State_KeySet;
55
56 size_t length;
57 const byte *iv = GetIVAndThrowIfInvalid(params, length);
58 if (iv)
59 Resynchronize(iv, (int)length);
60 }
61
62 void AuthenticatedSymmetricCipherBase::Resynchronize(const byte *iv, int length)
63 {
64 if (m_state < State_KeySet)
65 throw BadState(AlgorithmName(), "Resynchronize", "key is set");
66
67 m_bufferedDataLength = 0;
68 m_totalHeaderLength = m_totalMessageLength = m_totalFooterLength = 0;
69 m_state = State_KeySet;
70
71 Resync(iv, this->ThrowIfInvalidIVLength(length));
72 m_state = State_IVSet;
73 }
74
75 void AuthenticatedSymmetricCipherBase::Update(const byte *input, size_t length)
76 {
77 if (length == 0) {return;}
78
79 switch (m_state)
80 {
81 case State_Start:
82 case State_KeySet:
83 throw BadState(AlgorithmName(), "Update", "setting key and IV");
84 case State_IVSet:
85 AuthenticateData(input, length);
86 m_totalHeaderLength += length;
87 break;
88 case State_AuthUntransformed:
89 case State_AuthTransformed:
90 AuthenticateLastConfidentialBlock();
91 m_bufferedDataLength = 0;
92 m_state = State_AuthFooter;
93 // fall through
94 case State_AuthFooter:
95 AuthenticateData(input, length);
96 m_totalFooterLength += length;
97 break;
98 default:
99 CRYPTOPP_ASSERT(false);
100 }
101 }
102
103 void AuthenticatedSymmetricCipherBase::ProcessData(byte *outString, const byte *inString, size_t length)
104 {
105 m_totalMessageLength += length;
106 if (m_state >= State_IVSet && m_totalMessageLength > MaxMessageLength())
107 throw InvalidArgument(AlgorithmName() + ": message length exceeds maximum");
108
109 reswitch:
110 switch (m_state)
111 {
112 case State_Start:
113 case State_KeySet:
114 throw BadState(AlgorithmName(), "ProcessData", "setting key and IV");
115 case State_AuthFooter:
116 throw BadState(AlgorithmName(), "ProcessData was called after footer input has started");
117 case State_IVSet:
118 AuthenticateLastHeaderBlock();
119 m_bufferedDataLength = 0;
120 m_state = AuthenticationIsOnPlaintext()==IsForwardTransformation() ? State_AuthUntransformed : State_AuthTransformed;
121 goto reswitch;
122 case State_AuthUntransformed:
123 AuthenticateData(inString, length);
124 AccessSymmetricCipher().ProcessData(outString, inString, length);
125 break;
126 case State_AuthTransformed:
127 AccessSymmetricCipher().ProcessData(outString, inString, length);
128 AuthenticateData(outString, length);
129 break;
130 default:
131 CRYPTOPP_ASSERT(false);
132 }
133 }
134
135 void AuthenticatedSymmetricCipherBase::TruncatedFinal(byte *mac, size_t macSize)
136 {
137 if (m_totalHeaderLength > MaxHeaderLength())
138 throw InvalidArgument(AlgorithmName() + ": header length of " + IntToString(m_totalHeaderLength) + " exceeds the maximum of " + IntToString(MaxHeaderLength()));
139
140 if (m_totalFooterLength > MaxFooterLength())
141 {
142 if (MaxFooterLength() == 0)
143 throw InvalidArgument(AlgorithmName() + ": additional authenticated data (AAD) cannot be input after data to be encrypted or decrypted");
144 else
145 throw InvalidArgument(AlgorithmName() + ": footer length of " + IntToString(m_totalFooterLength) + " exceeds the maximum of " + IntToString(MaxFooterLength()));
146 }
147
148 switch (m_state)
149 {
150 case State_Start:
151 case State_KeySet:
152 throw BadState(AlgorithmName(), "TruncatedFinal", "setting key and IV");
153
154 case State_IVSet:
155 AuthenticateLastHeaderBlock();
156 m_bufferedDataLength = 0;
157 // fall through
158
159 case State_AuthUntransformed:
160 case State_AuthTransformed:
161 AuthenticateLastConfidentialBlock();
162 m_bufferedDataLength = 0;
163 // fall through
164
165 case State_AuthFooter:
166 AuthenticateLastFooterBlock(mac, macSize);
167 m_bufferedDataLength = 0;
168 break;
169
170 default:
171 CRYPTOPP_ASSERT(false);
172 }
173
174 m_state = State_KeySet;
175 }
176
177 NAMESPACE_END
178
179 #endif
InvalidArgument
An invalid argument was detected.
Definition: cryptlib.h:202
StreamTransformation::ProcessData
virtual void ProcessData(byte *outString, const byte *inString, size_t length)=0
Encrypt or decrypt an array of bytes.
AuthenticatedSymmetricCipherBase::ProcessData
void ProcessData(byte *outString, const byte *inString, size_t length)
Encrypt or decrypt an array of bytes.
Definition: authenc.cpp:103
AuthenticatedSymmetricCipher::BadState
Exception thrown when the object is in the wrong state for the operation.
Definition: cryptlib.h:1294
AuthenticatedSymmetricCipherBase::Resynchronize
void Resynchronize(const byte *iv, int length=-1)
Resynchronize with an IV.
Definition: authenc.cpp:62
AuthenticatedSymmetricCipher::MaxHeaderLength
virtual lword MaxHeaderLength() const =0
Provides the maximum length of AAD that can be input.
StreamTransformation::IsForwardTransformation
virtual bool IsForwardTransformation() const =0
Determines if the cipher is being operated in its forward direction.
AuthenticatedSymmetricCipherBase::SetKey
void SetKey(const byte *userKey, size_t keylength, const NameValuePairs &params)
Sets or reset the key of this object.
Definition: authenc.cpp:48
pch.h
Precompiled header file.
AuthenticatedSymmetricCipher::AlgorithmName
virtual std::string AlgorithmName() const
Provides the name of this algorithm.
Definition: cryptlib.cpp:265
CRYPTOPP_ASSERT
#define CRYPTOPP_ASSERT(exp)
Debugging and diagnostic assertion.
Definition: trap.h:60
SecBlock::begin
iterator begin()
Provides an iterator pointing to the first element in the memory block.
Definition: secblock.h:766
AuthenticatedSymmetricCipher::MaxMessageLength
virtual lword MaxMessageLength() const =0
Provides the maximum length of encrypted data.
AuthenticatedSymmetricCipherBase::Update
void Update(const byte *input, size_t length)
Updates a hash with additional input.
Definition: authenc.cpp:75
IntToString
std::string IntToString(T value, unsigned int base=10)
Converts a value to a string.
Definition: misc.h:632
CryptoPP
Crypto++ library namespace.
AuthenticatedSymmetricCipherBase::TruncatedFinal
void TruncatedFinal(byte *mac, size_t macSize)
Computes the hash of the current message.
Definition: authenc.cpp:135
AuthenticatedSymmetricCipher::MaxFooterLength
virtual lword MaxFooterLength() const
Provides the the maximum length of AAD.
Definition: cryptlib.h:1309
authenc.h
Classes for authenticated encryption modes of operation.
NameValuePairs
Interface for retrieving values given their names.
Definition: cryptlib.h:293