summaryrefslogtreecommitdiff
path: root/extra/yassl/taocrypt/src/hash.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'extra/yassl/taocrypt/src/hash.cpp')
-rw-r--r--extra/yassl/taocrypt/src/hash.cpp85
1 files changed, 85 insertions, 0 deletions
diff --git a/extra/yassl/taocrypt/src/hash.cpp b/extra/yassl/taocrypt/src/hash.cpp
index 66598177631..c51dc42a909 100644
--- a/extra/yassl/taocrypt/src/hash.cpp
+++ b/extra/yassl/taocrypt/src/hash.cpp
@@ -108,4 +108,89 @@ void HASHwithTransform::Final(byte* hash)
Init(); // reset state
}
+
+#ifdef WORD64_AVAILABLE
+
+HASH64withTransform::HASH64withTransform(word32 digSz, word32 buffSz)
+{
+ assert(digSz <= MaxDigestSz);
+ assert(buffSz <= MaxBufferSz);
+}
+
+
+void HASH64withTransform::AddLength(word32 len)
+{
+ HashLengthType tmp = loLen_;
+ if ( (loLen_ += len) < tmp)
+ hiLen_++; // carry low to high
+ hiLen_ += SafeRightShift<8*sizeof(HashLengthType)>(len);
+}
+
+
+// Update digest with data of size len, do in blocks
+void HASH64withTransform::Update(const byte* data, word32 len)
+{
+ // do block size increments
+ word32 blockSz = getBlockSize();
+ byte* local = reinterpret_cast<byte*>(buffer_);
+
+ while (len) {
+ word32 add = min(len, blockSz - buffLen_);
+ memcpy(&local[buffLen_], data, add);
+
+ buffLen_ += add;
+ data += add;
+ len -= add;
+
+ if (buffLen_ == blockSz) {
+ ByteReverseIf(buffer_, buffer_, blockSz, getByteOrder());
+ Transform();
+ AddLength(blockSz);
+ buffLen_ = 0;
+ }
+ }
+}
+
+
+// Final process, place digest in hash
+void HASH64withTransform::Final(byte* hash)
+{
+ word32 blockSz = getBlockSize();
+ word32 digestSz = getDigestSize();
+ word32 padSz = getPadSize();
+ ByteOrder order = getByteOrder();
+
+ AddLength(buffLen_); // before adding pads
+ HashLengthType preLoLen = GetBitCountLo();
+ HashLengthType preHiLen = GetBitCountHi();
+ byte* local = reinterpret_cast<byte*>(buffer_);
+
+ local[buffLen_++] = 0x80; // add 1
+
+ // pad with zeros
+ if (buffLen_ > padSz) {
+ memset(&local[buffLen_], 0, blockSz - buffLen_);
+ buffLen_ += blockSz - buffLen_;
+
+ ByteReverseIf(buffer_, buffer_, blockSz, order);
+ Transform();
+ buffLen_ = 0;
+ }
+ memset(&local[buffLen_], 0, padSz - buffLen_);
+
+ ByteReverseIf(buffer_, buffer_, padSz, order);
+
+ buffer_[blockSz / sizeof(word64) - 2] = order ? preHiLen : preLoLen;
+ buffer_[blockSz / sizeof(word64) - 1] = order ? preLoLen : preHiLen;
+
+ Transform();
+ ByteReverseIf(digest_, digest_, digestSz, order);
+ memcpy(hash, digest_, digestSz);
+
+ Init(); // reset state
+}
+
+#endif // WORD64_AVAILABLE
+
+
} // namespace