1 // blake2.h - written and placed in the public domain by Jeffrey Walton 2 // and Zooko Wilcox-O'Hearn. Based on Aumasson, Neves, 3 // Wilcox-O'Hearn and Winnerlein's reference BLAKE2 4 // implementation at http://github.com/BLAKE2/BLAKE2. 5 6 /// \file blake2.h 7 /// \brief Classes for BLAKE2b and BLAKE2s message digests and keyed message digests 8 /// \details This implementation follows Aumasson, Neves, Wilcox-O'Hearn and Winnerlein's 9 /// <A HREF="http://blake2.net/blake2.pdf">BLAKE2: simpler, smaller, fast as MD5</A> (2013.01.29). 10 /// Static algorithm name return either "BLAKE2b" or "BLAKE2s". An object algorithm name follows 11 /// the naming described in <A HREF="http://tools.ietf.org/html/rfc7693#section-4">RFC 7693, The 12 /// BLAKE2 Cryptographic Hash and Message Authentication Code (MAC)</A>. 13 /// \since C++ since Crypto++ 5.6.4, SSE since Crypto++ 5.6.4, NEON since Crypto++ 6.0, 14 /// Power8 since Crypto++ 8.0 15 16 #ifndef CRYPTOPP_BLAKE2_H 17 #define CRYPTOPP_BLAKE2_H 18 19 #include "cryptlib.h" 20 #include "secblock.h" 21 #include "seckey.h" 22 23 NAMESPACE_BEGIN(CryptoPP) 24 25 /// \brief BLAKE2s hash information 26 /// \since Crypto++ 5.6.4 27 struct BLAKE2s_Info : public VariableKeyLength<32,0,32,1,SimpleKeyingInterface::NOT_RESYNCHRONIZABLE> 28 { 29 typedef VariableKeyLength<32,0,32,1,SimpleKeyingInterface::NOT_RESYNCHRONIZABLE> KeyBase; 30 CRYPTOPP_CONSTANT(MIN_KEYLENGTH = KeyBase::MIN_KEYLENGTH); 31 CRYPTOPP_CONSTANT(MAX_KEYLENGTH = KeyBase::MAX_KEYLENGTH); 32 CRYPTOPP_CONSTANT(DEFAULT_KEYLENGTH = KeyBase::DEFAULT_KEYLENGTH); 33 34 CRYPTOPP_CONSTANT(BLOCKSIZE = 64); 35 CRYPTOPP_CONSTANT(DIGESTSIZE = 32); 36 CRYPTOPP_CONSTANT(SALTSIZE = 8); 37 CRYPTOPP_CONSTANT(PERSONALIZATIONSIZE = 8); 38 StaticAlgorithmNameBLAKE2s_Info39 CRYPTOPP_STATIC_CONSTEXPR const char* StaticAlgorithmName() {return "BLAKE2s";} 40 }; 41 42 /// \brief BLAKE2b hash information 43 /// \since Crypto++ 5.6.4 44 struct BLAKE2b_Info : public VariableKeyLength<64,0,64,1,SimpleKeyingInterface::NOT_RESYNCHRONIZABLE> 45 { 46 typedef VariableKeyLength<64,0,64,1,SimpleKeyingInterface::NOT_RESYNCHRONIZABLE> KeyBase; 47 CRYPTOPP_CONSTANT(MIN_KEYLENGTH = KeyBase::MIN_KEYLENGTH); 48 CRYPTOPP_CONSTANT(MAX_KEYLENGTH = KeyBase::MAX_KEYLENGTH); 49 CRYPTOPP_CONSTANT(DEFAULT_KEYLENGTH = KeyBase::DEFAULT_KEYLENGTH); 50 51 CRYPTOPP_CONSTANT(BLOCKSIZE = 128); 52 CRYPTOPP_CONSTANT(DIGESTSIZE = 64); 53 CRYPTOPP_CONSTANT(SALTSIZE = 16); 54 CRYPTOPP_CONSTANT(PERSONALIZATIONSIZE = 16); 55 StaticAlgorithmNameBLAKE2b_Info56 CRYPTOPP_STATIC_CONSTEXPR const char* StaticAlgorithmName() {return "BLAKE2b";} 57 }; 58 59 /// \brief BLAKE2s parameter block 60 struct CRYPTOPP_NO_VTABLE BLAKE2s_ParameterBlock 61 { 62 CRYPTOPP_CONSTANT(SALTSIZE = BLAKE2s_Info::SALTSIZE); 63 CRYPTOPP_CONSTANT(DIGESTSIZE = BLAKE2s_Info::DIGESTSIZE); 64 CRYPTOPP_CONSTANT(PERSONALIZATIONSIZE = BLAKE2s_Info::PERSONALIZATIONSIZE); 65 BLAKE2s_ParameterBlockBLAKE2s_ParameterBlock66 BLAKE2s_ParameterBlock() 67 { 68 Reset(); 69 } 70 BLAKE2s_ParameterBlockBLAKE2s_ParameterBlock71 BLAKE2s_ParameterBlock(size_t digestSize) 72 { 73 Reset(digestSize); 74 } 75 76 BLAKE2s_ParameterBlock(size_t digestSize, size_t keyLength, const byte* salt, size_t saltLength, 77 const byte* personalization, size_t personalizationLength); 78 79 void Reset(size_t digestLength=DIGESTSIZE, size_t keyLength=0); 80 dataBLAKE2s_ParameterBlock81 byte* data() { 82 return m_data.data(); 83 } 84 dataBLAKE2s_ParameterBlock85 const byte* data() const { 86 return m_data.data(); 87 } 88 sizeBLAKE2s_ParameterBlock89 size_t size() const { 90 return m_data.size(); 91 } 92 saltBLAKE2s_ParameterBlock93 byte* salt() { 94 return m_data + SaltOff; 95 } 96 personalizationBLAKE2s_ParameterBlock97 byte* personalization() { 98 return m_data + PersonalizationOff; 99 } 100 101 // Offsets into the byte array 102 enum { 103 DigestOff = 0, KeyOff = 1, FanoutOff = 2, DepthOff = 3, LeafOff = 4, NodeOff = 8, 104 NodeDepthOff = 14, InnerOff = 15, SaltOff = 16, PersonalizationOff = 24 105 }; 106 107 FixedSizeAlignedSecBlock<byte, 32, true> m_data; 108 }; 109 110 /// \brief BLAKE2b parameter block 111 struct CRYPTOPP_NO_VTABLE BLAKE2b_ParameterBlock 112 { 113 CRYPTOPP_CONSTANT(SALTSIZE = BLAKE2b_Info::SALTSIZE); 114 CRYPTOPP_CONSTANT(DIGESTSIZE = BLAKE2b_Info::DIGESTSIZE); 115 CRYPTOPP_CONSTANT(PERSONALIZATIONSIZE = BLAKE2b_Info::PERSONALIZATIONSIZE); 116 BLAKE2b_ParameterBlockBLAKE2b_ParameterBlock117 BLAKE2b_ParameterBlock() 118 { 119 Reset(); 120 } 121 BLAKE2b_ParameterBlockBLAKE2b_ParameterBlock122 BLAKE2b_ParameterBlock(size_t digestSize) 123 { 124 Reset(digestSize); 125 } 126 127 BLAKE2b_ParameterBlock(size_t digestSize, size_t keyLength, const byte* salt, size_t saltLength, 128 const byte* personalization, size_t personalizationLength); 129 130 void Reset(size_t digestLength=DIGESTSIZE, size_t keyLength=0); 131 dataBLAKE2b_ParameterBlock132 byte* data() { 133 return m_data.data(); 134 } 135 dataBLAKE2b_ParameterBlock136 const byte* data() const { 137 return m_data.data(); 138 } 139 sizeBLAKE2b_ParameterBlock140 size_t size() const { 141 return m_data.size(); 142 } 143 saltBLAKE2b_ParameterBlock144 byte* salt() { 145 return m_data + SaltOff; 146 } 147 personalizationBLAKE2b_ParameterBlock148 byte* personalization() { 149 return m_data + PersonalizationOff; 150 } 151 152 // Offsets into the byte array 153 enum { 154 DigestOff = 0, KeyOff = 1, FanoutOff = 2, DepthOff = 3, LeafOff = 4, NodeOff = 8, 155 NodeDepthOff = 16, InnerOff = 17, RfuOff = 18, SaltOff = 32, PersonalizationOff = 48 156 }; 157 158 FixedSizeAlignedSecBlock<byte, 64, true> m_data; 159 }; 160 161 /// \brief BLAKE2s state information 162 /// \since Crypto++ 5.6.4 163 struct CRYPTOPP_NO_VTABLE BLAKE2s_State 164 { BLAKE2s_StateBLAKE2s_State165 BLAKE2s_State() { 166 Reset(); 167 } 168 169 void Reset(); 170 hBLAKE2s_State171 inline word32* h() { 172 return m_hft.data(); 173 } 174 tBLAKE2s_State175 inline word32* t() { 176 return m_hft.data() + 8; 177 } 178 fBLAKE2s_State179 inline word32* f() { 180 return m_hft.data() + 10; 181 } 182 dataBLAKE2s_State183 inline byte* data() { 184 return m_buf.data(); 185 } 186 187 // SSE4, Power7 and NEON depend upon t[] and f[] being side-by-side 188 CRYPTOPP_CONSTANT(BLOCKSIZE = BLAKE2s_Info::BLOCKSIZE); 189 FixedSizeAlignedSecBlock<word32, 8+2+2, true> m_hft; 190 FixedSizeAlignedSecBlock<byte, BLOCKSIZE, true> m_buf; 191 size_t m_len; 192 }; 193 194 /// \brief BLAKE2b state information 195 /// \since Crypto++ 5.6.4 196 struct CRYPTOPP_NO_VTABLE BLAKE2b_State 197 { BLAKE2b_StateBLAKE2b_State198 BLAKE2b_State() { 199 Reset(); 200 } 201 202 void Reset(); 203 hBLAKE2b_State204 inline word64* h() { 205 return m_hft.data(); 206 } 207 tBLAKE2b_State208 inline word64* t() { 209 return m_hft.data() + 8; 210 } 211 fBLAKE2b_State212 inline word64* f() { 213 return m_hft.data() + 10; 214 } 215 dataBLAKE2b_State216 inline byte* data() { 217 return m_buf.data(); 218 } 219 220 // SSE4, Power8 and NEON depend upon t[] and f[] being side-by-side 221 CRYPTOPP_CONSTANT(BLOCKSIZE = BLAKE2b_Info::BLOCKSIZE); 222 FixedSizeAlignedSecBlock<word64, 8+2+2, true> m_hft; 223 FixedSizeAlignedSecBlock<byte, BLOCKSIZE, true> m_buf; 224 size_t m_len; 225 }; 226 227 /// \brief The BLAKE2s cryptographic hash function 228 /// \details BLAKE2s can function as both a hash and keyed hash. If you want only the hash, 229 /// then use the BLAKE2s constructor that accepts no parameters or digest size. If you 230 /// want a keyed hash, then use the constructor that accpts the key as a parameter. 231 /// Once a key and digest size are selected, its effectively immutable. The Restart() 232 /// method that accepts a ParameterBlock does not allow you to change it. 233 /// \sa Aumasson, Neves, Wilcox-O'Hearn and Winnerlein's 234 /// <A HREF="http://blake2.net/blake2.pdf">BLAKE2: simpler, smaller, fast as MD5</A> (2013.01.29). 235 /// \since C++ since Crypto++ 5.6.4, SSE since Crypto++ 5.6.4, NEON since Crypto++ 6.0, 236 /// Power8 since Crypto++ 8.0 237 class BLAKE2s : public SimpleKeyingInterfaceImpl<MessageAuthenticationCode, BLAKE2s_Info> 238 { 239 public: 240 CRYPTOPP_CONSTANT(DEFAULT_KEYLENGTH = BLAKE2s_Info::DEFAULT_KEYLENGTH); 241 CRYPTOPP_CONSTANT(MIN_KEYLENGTH = BLAKE2s_Info::MIN_KEYLENGTH); 242 CRYPTOPP_CONSTANT(MAX_KEYLENGTH = BLAKE2s_Info::MAX_KEYLENGTH); 243 244 CRYPTOPP_CONSTANT(DIGESTSIZE = BLAKE2s_Info::DIGESTSIZE); 245 CRYPTOPP_CONSTANT(BLOCKSIZE = BLAKE2s_Info::BLOCKSIZE); 246 CRYPTOPP_CONSTANT(SALTSIZE = BLAKE2s_Info::SALTSIZE); 247 CRYPTOPP_CONSTANT(PERSONALIZATIONSIZE = BLAKE2s_Info::PERSONALIZATIONSIZE); 248 249 typedef BLAKE2s_State State; 250 typedef BLAKE2s_ParameterBlock ParameterBlock; 251 StaticAlgorithmName()252 CRYPTOPP_STATIC_CONSTEXPR const char* StaticAlgorithmName() {return "BLAKE2s";} 253 ~BLAKE2s()254 virtual ~BLAKE2s() {} 255 256 /// \brief Construct a BLAKE2s hash 257 /// \param digestSize the digest size, in bytes 258 /// \param treeMode flag indicating tree mode 259 /// \since Crypto++ 5.6.4 260 BLAKE2s(bool treeMode=false, unsigned int digestSize = DIGESTSIZE); 261 262 /// \brief Construct a BLAKE2s hash 263 /// \param digestSize the digest size, in bytes 264 /// \details treeMode flag is set to false 265 /// \since Crypto++ 8.2 266 BLAKE2s(unsigned int digestSize); 267 268 /// \brief Construct a BLAKE2s hash 269 /// \param key a byte array used to key the cipher 270 /// \param keyLength the size of the byte array 271 /// \param salt a byte array used as salt 272 /// \param saltLength the size of the byte array 273 /// \param personalization a byte array used as personalization string 274 /// \param personalizationLength the size of the byte array 275 /// \param treeMode flag indicating tree mode 276 /// \param digestSize the digest size, in bytes 277 /// \since Crypto++ 5.6.4 278 BLAKE2s(const byte *key, size_t keyLength, const byte* salt = NULLPTR, size_t saltLength = 0, 279 const byte* personalization = NULLPTR, size_t personalizationLength = 0, 280 bool treeMode=false, unsigned int digestSize = DIGESTSIZE); 281 282 /// \brief Retrieve the object's name 283 /// \return the object's algorithm name following RFC 7693 284 /// \details Object algorithm name follows the naming described in 285 /// <A HREF="http://tools.ietf.org/html/rfc7693#section-4">RFC 7693, The BLAKE2 Cryptographic Hash and 286 /// Message Authentication Code (MAC)</A>. For example, "BLAKE2b-512" and "BLAKE2s-256". AlgorithmName()287 std::string AlgorithmName() const {return std::string(BLAKE2s_Info::StaticAlgorithmName()) + "-" + IntToString(DigestSize()*8);} 288 BlockSize()289 unsigned int BlockSize() const {return BLOCKSIZE;} DigestSize()290 unsigned int DigestSize() const {return m_digestSize;} 291 unsigned int OptimalDataAlignment() const; 292 293 void Update(const byte *input, size_t length); 294 void Restart(); 295 296 /// \brief Restart a hash with parameter block and counter 297 /// \param block parameter block 298 /// \param counter counter array 299 /// \details Parameter block is persisted across calls to Restart(). 300 void Restart(const BLAKE2s_ParameterBlock& block, const word32 counter[2]); 301 302 /// \brief Set tree mode 303 /// \param mode the new tree mode 304 /// \details BLAKE2 has two finalization flags, called State::f[0] and State::f[1]. 305 /// If <tt>treeMode=false</tt> (default), then State::f[1] is never set. If 306 /// <tt>treeMode=true</tt>, then State::f[1] is set when State::f[0] is set. 307 /// Tree mode is persisted across calls to Restart(). SetTreeMode(bool mode)308 void SetTreeMode(bool mode) {m_treeMode=mode;} 309 310 /// \brief Get tree mode 311 /// \return the current tree mode 312 /// \details Tree mode is persisted across calls to Restart(). GetTreeMode()313 bool GetTreeMode() const {return m_treeMode;} 314 315 void TruncatedFinal(byte *hash, size_t size); 316 317 std::string AlgorithmProvider() const; 318 319 protected: 320 // Operates on state buffer and/or input. Must be BLOCKSIZE, final block will pad with 0's. 321 void Compress(const byte *input); 322 inline void IncrementCounter(size_t count=BLOCKSIZE); 323 324 void UncheckedSetKey(const byte* key, unsigned int length, const CryptoPP::NameValuePairs& params); 325 326 private: 327 State m_state; 328 ParameterBlock m_block; 329 AlignedSecByteBlock m_key; 330 word32 m_digestSize, m_keyLength; 331 bool m_treeMode; 332 }; 333 334 /// \brief The BLAKE2b cryptographic hash function 335 /// \details BLAKE2b can function as both a hash and keyed hash. If you want only the hash, 336 /// then use the BLAKE2b constructor that accepts no parameters or digest size. If you 337 /// want a keyed hash, then use the constructor that accpts the key as a parameter. 338 /// Once a key and digest size are selected, its effectively immutable. The Restart() 339 /// method that accepts a ParameterBlock does not allow you to change it. 340 /// \sa Aumasson, Neves, Wilcox-O'Hearn and Winnerlein's 341 /// <A HREF="http://blake2.net/blake2.pdf">BLAKE2: simpler, smaller, fast as MD5</A> (2013.01.29). 342 /// \since C++ since Crypto++ 5.6.4, SSE since Crypto++ 5.6.4, NEON since Crypto++ 6.0, 343 /// Power8 since Crypto++ 8.0 344 class BLAKE2b : public SimpleKeyingInterfaceImpl<MessageAuthenticationCode, BLAKE2b_Info> 345 { 346 public: 347 CRYPTOPP_CONSTANT(DEFAULT_KEYLENGTH = BLAKE2b_Info::DEFAULT_KEYLENGTH); 348 CRYPTOPP_CONSTANT(MIN_KEYLENGTH = BLAKE2b_Info::MIN_KEYLENGTH); 349 CRYPTOPP_CONSTANT(MAX_KEYLENGTH = BLAKE2b_Info::MAX_KEYLENGTH); 350 351 CRYPTOPP_CONSTANT(DIGESTSIZE = BLAKE2b_Info::DIGESTSIZE); 352 CRYPTOPP_CONSTANT(BLOCKSIZE = BLAKE2b_Info::BLOCKSIZE); 353 CRYPTOPP_CONSTANT(SALTSIZE = BLAKE2b_Info::SALTSIZE); 354 CRYPTOPP_CONSTANT(PERSONALIZATIONSIZE = BLAKE2b_Info::PERSONALIZATIONSIZE); 355 356 typedef BLAKE2b_State State; 357 typedef BLAKE2b_ParameterBlock ParameterBlock; 358 StaticAlgorithmName()359 CRYPTOPP_STATIC_CONSTEXPR const char* StaticAlgorithmName() {return "BLAKE2b";} 360 ~BLAKE2b()361 virtual ~BLAKE2b() {} 362 363 /// \brief Construct a BLAKE2b hash 364 /// \param digestSize the digest size, in bytes 365 /// \param treeMode flag indicating tree mode 366 /// \since Crypto++ 5.6.4 367 BLAKE2b(bool treeMode=false, unsigned int digestSize = DIGESTSIZE); 368 369 /// \brief Construct a BLAKE2s hash 370 /// \param digestSize the digest size, in bytes 371 /// \details treeMode flag is set to false 372 /// \since Crypto++ 8.2 373 BLAKE2b(unsigned int digestSize); 374 375 /// \brief Construct a BLAKE2b hash 376 /// \param key a byte array used to key the cipher 377 /// \param keyLength the size of the byte array 378 /// \param salt a byte array used as salt 379 /// \param saltLength the size of the byte array 380 /// \param personalization a byte array used as personalization string 381 /// \param personalizationLength the size of the byte array 382 /// \param treeMode flag indicating tree mode 383 /// \param digestSize the digest size, in bytes 384 /// \since Crypto++ 5.6.4 385 BLAKE2b(const byte *key, size_t keyLength, const byte* salt = NULLPTR, size_t saltLength = 0, 386 const byte* personalization = NULLPTR, size_t personalizationLength = 0, 387 bool treeMode=false, unsigned int digestSize = DIGESTSIZE); 388 389 /// \brief Retrieve the object's name 390 /// \return the object's algorithm name following RFC 7693 391 /// \details Object algorithm name follows the naming described in 392 /// <A HREF="http://tools.ietf.org/html/rfc7693#section-4">RFC 7693, The BLAKE2 Cryptographic Hash and 393 /// Message Authentication Code (MAC)</A>. For example, "BLAKE2b-512" and "BLAKE2s-256". AlgorithmName()394 std::string AlgorithmName() const {return std::string(BLAKE2b_Info::StaticAlgorithmName()) + "-" + IntToString(DigestSize()*8);} 395 BlockSize()396 unsigned int BlockSize() const {return BLOCKSIZE;} DigestSize()397 unsigned int DigestSize() const {return m_digestSize;} 398 unsigned int OptimalDataAlignment() const; 399 400 void Update(const byte *input, size_t length); 401 void Restart(); 402 403 /// \brief Restart a hash with parameter block and counter 404 /// \param block parameter block 405 /// \param counter counter array 406 /// \details Parameter block is persisted across calls to Restart(). 407 void Restart(const BLAKE2b_ParameterBlock& block, const word64 counter[2]); 408 409 /// \brief Set tree mode 410 /// \param mode the new tree mode 411 /// \details BLAKE2 has two finalization flags, called State::f[0] and State::f[1]. 412 /// If <tt>treeMode=false</tt> (default), then State::f[1] is never set. If 413 /// <tt>treeMode=true</tt>, then State::f[1] is set when State::f[0] is set. 414 /// Tree mode is persisted across calls to Restart(). SetTreeMode(bool mode)415 void SetTreeMode(bool mode) {m_treeMode=mode;} 416 417 /// \brief Get tree mode 418 /// \return the current tree mode 419 /// \details Tree mode is persisted across calls to Restart(). GetTreeMode()420 bool GetTreeMode() const {return m_treeMode;} 421 422 void TruncatedFinal(byte *hash, size_t size); 423 424 std::string AlgorithmProvider() const; 425 426 protected: 427 428 // Operates on state buffer and/or input. Must be BLOCKSIZE, final block will pad with 0's. 429 void Compress(const byte *input); 430 inline void IncrementCounter(size_t count=BLOCKSIZE); 431 432 void UncheckedSetKey(const byte* key, unsigned int length, const CryptoPP::NameValuePairs& params); 433 434 private: 435 State m_state; 436 ParameterBlock m_block; 437 AlignedSecByteBlock m_key; 438 word32 m_digestSize, m_keyLength; 439 bool m_treeMode; 440 }; 441 442 NAMESPACE_END 443 444 #endif 445