Test OOP wrappers
import std.conv : hexString; SHA3_224Digest sha3_224 = new SHA3_224Digest(); assert(sha3_224.finish() == cast(ubyte[]) hexString! "6b4e03423667dbb73b6e15454f0eb1abd4597f9a1b078e3f5b5a6bc7"); SHA3_256Digest sha3_256 = new SHA3_256Digest(); assert(sha3_256.finish() == cast(ubyte[]) hexString! "a7ffc6f8bf1ed76651c14756a061d662f580ff4de43b49fa82d80a4b80f8434a"); SHA3_384Digest sha3_384 = new SHA3_384Digest(); assert(sha3_384.finish() == cast(ubyte[]) hexString!( "0c63a75b845e4f7d01107d852e4c2485c51a50aaaa94fc61995e71bbee983a2a"~ "c3713831264adb47fb6bd1e058d5f004")); SHA3_512Digest sha3_512 = new SHA3_512Digest(); assert(sha3_512.finish() == cast(ubyte[]) hexString!( "a69f73cca23a9ac5c8b567dc185a756e97c982164fe25859e0d1dcc1475c80a6"~ "15b2123af1f5f94c11e3e9402c3ac558f500199d95b6d3e301758586281dcd26")); SHAKE128Digest shake128 = new SHAKE128Digest(); assert(shake128.finish() == cast(ubyte[]) hexString!( "7f9c2ba4e88f827d616045507605853e")); SHAKE256Digest shake256 = new SHAKE256Digest(); assert(shake256.finish() == cast(ubyte[]) hexString!( "46b9dd2b0ba88d13233b3feb743eeb243fcd52ea62b81b82b50c27646ed5762f"));
Testing with HMAC
// NOTE: OpenSSL (even 3.0.1) is incapable of producing a hash with // SHAKE and HMAC, but should work since unittests for // SHAKE-related hashes (including XOFs) are passing. import std.ascii : LetterCase; import std.string : representation; import std.digest.hmac : hmac; auto secret = "secret".representation; assert("The quick brown fox jumps over the lazy dog" .representation .hmac!SHA3_256(secret) .toHexString!(LetterCase.lower) == "93379fab68fae6d0fde0c816ea8a49fbd3c80f136c6af08bc61df5268d01b4d8"); assert("The quick brown fox jumps over the lazy dog" .representation .hmac!SHA3_512(secret) .toHexString!(LetterCase.lower) == "394e52da72b28bab49174a0d22cd48eac415de750027e6485ceb945b9948d8ae"~ "e656e61e217ac1352a41c66454e2a9ae830fddbdf4f8aa6215c586b88e158ee8");
Testing out various SHAKE XOFs.
import std.conv : hexString; // SHAKE128("", 256) auto shake128_256empty = hexString!( "7f9c2ba4e88f827d616045507605853ed73b8093f6efbc88eb1a6eacfa66ef26"); // SHAKE256("", 512) auto shake256_512empty = hexString!( "46b9dd2b0ba88d13233b3feb743eeb243fcd52ea62b81b82b50c27646ed5762f"~ "d75dc4ddd8c0f200cb05019d67b592f6fc821c49479ab48640292eacb3b7c4be"); // SHAKE-128/256 alias SHAKE128_256 = KECCAK!(128, 256); alias SHAKE128_256Digest = WrapperDigest!SHAKE128_256; auto shake128_256Of(T...)(T data) { return digest!(SHAKE128_256, T)(data); } // Template API assert(shake128_256Of("") == shake128_256empty); // OOP API Digest shake128_256 = new SHAKE128_256Digest(); assert(shake128_256.finish() == shake128_256empty); // SHAKE-256/512 alias SHAKE256_512 = KECCAK!(256, 512); alias SHAKE256_512Digest = WrapperDigest!SHAKE256_512; auto shake256_512Of(T...)(T data) { return digest!(SHAKE256_512, T)(data); } // Template API assert(shake256_512Of("") == shake256_512empty); // OOP API Digest shake256_512 = new SHAKE256_512Digest(); assert(shake256_512.finish() == shake256_512empty);
OOP API SHA-3/SHAKE implementation aliases.