finish method
Pads, compresses the final block(s), and returns the digest. The hash cannot be updated afterwards; snapshot with copy first to continue a running stream.
Implementation
Uint8List finish() {
if (_finished) {
throw StateError('finish() called twice');
}
_finished = true;
final bytes = _totalBytes;
_buffer[_bufferLength++] = 0x80;
if (_bufferLength > blockSize - 8) {
_buffer.fillRange(_bufferLength, blockSize, 0);
compress(_buffer, 0);
_bufferLength = 0;
}
_buffer.fillRange(_bufferLength, blockSize - 8, 0);
// 64-bit big-endian bit count, kept within web-safe arithmetic: the
// high word via division, the low word from the 29 low bits only,
// no shift ever sees a value ≥ 2^32 (a dart2js gotcha).
final high = bytes ~/ 0x20000000;
final low = (bytes & 0x1FFFFFFF) << 3;
_buffer[blockSize - 8] = (high >>> 24) & 0xFF;
_buffer[blockSize - 7] = (high >>> 16) & 0xFF;
_buffer[blockSize - 6] = (high >>> 8) & 0xFF;
_buffer[blockSize - 5] = high & 0xFF;
_buffer[blockSize - 4] = low >>> 24;
_buffer[blockSize - 3] = (low >>> 16) & 0xFF;
_buffer[blockSize - 2] = (low >>> 8) & 0xFF;
_buffer[blockSize - 1] = low & 0xFF;
compress(_buffer, 0);
final out = Uint8List(digestSize);
writeDigest(out);
return out;
}