1/* 2 * FIPS-202 compliant SHA3 implementation 3 * 4 * Copyright The Mbed TLS Contributors 5 * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later 6 */ 7/* 8 * The SHA-3 Secure Hash Standard was published by NIST in 2015. 9 * 10 * https://nvlpubs.nist.gov/nistpubs/fips/nist.fips.202.pdf 11 */ 12 13#include "common.h" 14 15#if defined(MBEDTLS_SHA3_C) 16 17/* 18 * These macros select manually unrolled implementations of parts of the main permutation function. 19 * 20 * Unrolling has a major impact on both performance and code size. gcc performance benefits a lot 21 * from manually unrolling at higher optimisation levels. 22 * 23 * Depending on your size/perf priorities, compiler and target, it may be beneficial to adjust 24 * these; the defaults here should give sensible trade-offs for gcc and clang on aarch64 and 25 * x86-64. 26 */ 27#if !defined(MBEDTLS_SHA3_THETA_UNROLL) 28 #define MBEDTLS_SHA3_THETA_UNROLL 0 //no-check-names 29#endif 30#if !defined(MBEDTLS_SHA3_CHI_UNROLL) 31 #if defined(__OPTIMIZE_SIZE__) 32 #define MBEDTLS_SHA3_CHI_UNROLL 0 //no-check-names 33 #else 34 #define MBEDTLS_SHA3_CHI_UNROLL 1 //no-check-names 35 #endif 36#endif 37#if !defined(MBEDTLS_SHA3_PI_UNROLL) 38 #define MBEDTLS_SHA3_PI_UNROLL 1 //no-check-names 39#endif 40#if !defined(MBEDTLS_SHA3_RHO_UNROLL) 41 #define MBEDTLS_SHA3_RHO_UNROLL 1 //no-check-names 42#endif 43 44#include "mbedtls/sha3.h" 45#include "mbedtls/platform_util.h" 46#include "mbedtls/error.h" 47 48#include <string.h> 49 50#if defined(MBEDTLS_SELF_TEST) 51#include "mbedtls/platform.h" 52#endif /* MBEDTLS_SELF_TEST */ 53 54#define XOR_BYTE 0x6 55 56/* Precomputed masks for the iota transform. 57 * 58 * Each round uses a 64-bit mask value. In each mask values, only 59 * bits whose position is of the form 2^k-1 can be set, thus only 60 * 7 of 64 bits of the mask need to be known for each mask value. 61 * 62 * We use a compressed encoding of the mask where bits 63, 31 and 15 63 * are moved to bits 4-6. This allows us to make each mask value 64 * 1 byte rather than 8 bytes, saving 7*24 = 168 bytes of data (with 65 * perhaps a little variation due to alignment). Decompressing this 66 * requires a little code, but much less than the savings on the table. 67 * 68 * The impact on performance depends on the platform and compiler. 69 * There's a bit more computation, but less memory bandwidth. A quick 70 * benchmark on x86_64 shows a 7% speed improvement with GCC and a 71 * 5% speed penalty with Clang, compared to the naive uint64_t[24] table. 72 * YMMV. 73 */ 74/* Helper macro to set the values of the higher bits in unused low positions */ 75#define H(b63, b31, b15) (b63 << 6 | b31 << 5 | b15 << 4) 76static const uint8_t iota_r_packed[24] = { 77 H(0, 0, 0) | 0x01, H(0, 0, 1) | 0x82, H(1, 0, 1) | 0x8a, H(1, 1, 1) | 0x00, 78 H(0, 0, 1) | 0x8b, H(0, 1, 0) | 0x01, H(1, 1, 1) | 0x81, H(1, 0, 1) | 0x09, 79 H(0, 0, 0) | 0x8a, H(0, 0, 0) | 0x88, H(0, 1, 1) | 0x09, H(0, 1, 0) | 0x0a, 80 H(0, 1, 1) | 0x8b, H(1, 0, 0) | 0x8b, H(1, 0, 1) | 0x89, H(1, 0, 1) | 0x03, 81 H(1, 0, 1) | 0x02, H(1, 0, 0) | 0x80, H(0, 0, 1) | 0x0a, H(1, 1, 0) | 0x0a, 82 H(1, 1, 1) | 0x81, H(1, 0, 1) | 0x80, H(0, 1, 0) | 0x01, H(1, 1, 1) | 0x08, 83}; 84#undef H 85 86static const uint32_t rho[6] = { 87 0x3f022425, 0x1c143a09, 0x2c3d3615, 0x27191713, 0x312b382e, 0x3e030832 88}; 89 90static const uint32_t pi[6] = { 91 0x110b070a, 0x10050312, 0x04181508, 0x0d13170f, 0x0e14020c, 0x01060916 92}; 93 94#define ROTR64(x, y) (((x) << (64U - (y))) | ((x) >> (y))) // 64-bit rotate right 95#define ABSORB(ctx, idx, v) do { ctx->state[(idx) >> 3] ^= ((uint64_t) (v)) << (((idx) & 0x7) << 3); \ 96} while (0) 97#define SQUEEZE(ctx, idx) ((uint8_t) (ctx->state[(idx) >> 3] >> (((idx) & 0x7) << 3))) 98#define SWAP(x, y) do { uint64_t tmp = (x); (x) = (y); (y) = tmp; } while (0) 99 100/* The permutation function. */ 101static void keccak_f1600(mbedtls_sha3_context *ctx) 102{ 103 uint64_t lane[5]; 104 uint64_t *s = ctx->state; 105 int i; 106 107 for (int round = 0; round < 24; round++) { 108 uint64_t t; 109 110 /* Theta */ 111#if MBEDTLS_SHA3_THETA_UNROLL == 0 //no-check-names 112 for (i = 0; i < 5; i++) { 113 lane[i] = s[i] ^ s[i + 5] ^ s[i + 10] ^ s[i + 15] ^ s[i + 20]; 114 } 115 for (i = 0; i < 5; i++) { 116 t = lane[(i + 4) % 5] ^ ROTR64(lane[(i + 1) % 5], 63); 117 s[i] ^= t; s[i + 5] ^= t; s[i + 10] ^= t; s[i + 15] ^= t; s[i + 20] ^= t; 118 } 119#else 120 lane[0] = s[0] ^ s[5] ^ s[10] ^ s[15] ^ s[20]; 121 lane[1] = s[1] ^ s[6] ^ s[11] ^ s[16] ^ s[21]; 122 lane[2] = s[2] ^ s[7] ^ s[12] ^ s[17] ^ s[22]; 123 lane[3] = s[3] ^ s[8] ^ s[13] ^ s[18] ^ s[23]; 124 lane[4] = s[4] ^ s[9] ^ s[14] ^ s[19] ^ s[24]; 125 126 t = lane[4] ^ ROTR64(lane[1], 63); 127 s[0] ^= t; s[5] ^= t; s[10] ^= t; s[15] ^= t; s[20] ^= t; 128 129 t = lane[0] ^ ROTR64(lane[2], 63); 130 s[1] ^= t; s[6] ^= t; s[11] ^= t; s[16] ^= t; s[21] ^= t; 131 132 t = lane[1] ^ ROTR64(lane[3], 63); 133 s[2] ^= t; s[7] ^= t; s[12] ^= t; s[17] ^= t; s[22] ^= t; 134 135 t = lane[2] ^ ROTR64(lane[4], 63); 136 s[3] ^= t; s[8] ^= t; s[13] ^= t; s[18] ^= t; s[23] ^= t; 137 138 t = lane[3] ^ ROTR64(lane[0], 63); 139 s[4] ^= t; s[9] ^= t; s[14] ^= t; s[19] ^= t; s[24] ^= t; 140#endif 141 142 /* Rho */ 143 for (i = 1; i < 25; i += 4) { 144 uint32_t r = rho[(i - 1) >> 2]; 145#if MBEDTLS_SHA3_RHO_UNROLL == 0 146 for (int j = i; j < i + 4; j++) { 147 uint8_t r8 = (uint8_t) (r >> 24); 148 r <<= 8; 149 s[j] = ROTR64(s[j], r8); 150 } 151#else 152 s[i + 0] = ROTR64(s[i + 0], MBEDTLS_BYTE_3(r)); 153 s[i + 1] = ROTR64(s[i + 1], MBEDTLS_BYTE_2(r)); 154 s[i + 2] = ROTR64(s[i + 2], MBEDTLS_BYTE_1(r)); 155 s[i + 3] = ROTR64(s[i + 3], MBEDTLS_BYTE_0(r)); 156#endif 157 } 158 159 /* Pi */ 160 t = s[1]; 161#if MBEDTLS_SHA3_PI_UNROLL == 0 162 for (i = 0; i < 24; i += 4) { 163 uint32_t p = pi[i >> 2]; 164 for (unsigned j = 0; j < 4; j++) { 165 SWAP(s[p & 0xff], t); 166 p >>= 8; 167 } 168 } 169#else 170 uint32_t p = pi[0]; 171 SWAP(s[MBEDTLS_BYTE_0(p)], t); SWAP(s[MBEDTLS_BYTE_1(p)], t); 172 SWAP(s[MBEDTLS_BYTE_2(p)], t); SWAP(s[MBEDTLS_BYTE_3(p)], t); 173 p = pi[1]; 174 SWAP(s[MBEDTLS_BYTE_0(p)], t); SWAP(s[MBEDTLS_BYTE_1(p)], t); 175 SWAP(s[MBEDTLS_BYTE_2(p)], t); SWAP(s[MBEDTLS_BYTE_3(p)], t); 176 p = pi[2]; 177 SWAP(s[MBEDTLS_BYTE_0(p)], t); SWAP(s[MBEDTLS_BYTE_1(p)], t); 178 SWAP(s[MBEDTLS_BYTE_2(p)], t); SWAP(s[MBEDTLS_BYTE_3(p)], t); 179 p = pi[3]; 180 SWAP(s[MBEDTLS_BYTE_0(p)], t); SWAP(s[MBEDTLS_BYTE_1(p)], t); 181 SWAP(s[MBEDTLS_BYTE_2(p)], t); SWAP(s[MBEDTLS_BYTE_3(p)], t); 182 p = pi[4]; 183 SWAP(s[MBEDTLS_BYTE_0(p)], t); SWAP(s[MBEDTLS_BYTE_1(p)], t); 184 SWAP(s[MBEDTLS_BYTE_2(p)], t); SWAP(s[MBEDTLS_BYTE_3(p)], t); 185 p = pi[5]; 186 SWAP(s[MBEDTLS_BYTE_0(p)], t); SWAP(s[MBEDTLS_BYTE_1(p)], t); 187 SWAP(s[MBEDTLS_BYTE_2(p)], t); SWAP(s[MBEDTLS_BYTE_3(p)], t); 188#endif 189 190 /* Chi */ 191#if MBEDTLS_SHA3_CHI_UNROLL == 0 //no-check-names 192 for (i = 0; i <= 20; i += 5) { 193 lane[0] = s[i]; lane[1] = s[i + 1]; lane[2] = s[i + 2]; 194 lane[3] = s[i + 3]; lane[4] = s[i + 4]; 195 s[i + 0] ^= (~lane[1]) & lane[2]; 196 s[i + 1] ^= (~lane[2]) & lane[3]; 197 s[i + 2] ^= (~lane[3]) & lane[4]; 198 s[i + 3] ^= (~lane[4]) & lane[0]; 199 s[i + 4] ^= (~lane[0]) & lane[1]; 200 } 201#else 202 lane[0] = s[0]; lane[1] = s[1]; lane[2] = s[2]; lane[3] = s[3]; lane[4] = s[4]; 203 s[0] ^= (~lane[1]) & lane[2]; 204 s[1] ^= (~lane[2]) & lane[3]; 205 s[2] ^= (~lane[3]) & lane[4]; 206 s[3] ^= (~lane[4]) & lane[0]; 207 s[4] ^= (~lane[0]) & lane[1]; 208 209 lane[0] = s[5]; lane[1] = s[6]; lane[2] = s[7]; lane[3] = s[8]; lane[4] = s[9]; 210 s[5] ^= (~lane[1]) & lane[2]; 211 s[6] ^= (~lane[2]) & lane[3]; 212 s[7] ^= (~lane[3]) & lane[4]; 213 s[8] ^= (~lane[4]) & lane[0]; 214 s[9] ^= (~lane[0]) & lane[1]; 215 216 lane[0] = s[10]; lane[1] = s[11]; lane[2] = s[12]; lane[3] = s[13]; lane[4] = s[14]; 217 s[10] ^= (~lane[1]) & lane[2]; 218 s[11] ^= (~lane[2]) & lane[3]; 219 s[12] ^= (~lane[3]) & lane[4]; 220 s[13] ^= (~lane[4]) & lane[0]; 221 s[14] ^= (~lane[0]) & lane[1]; 222 223 lane[0] = s[15]; lane[1] = s[16]; lane[2] = s[17]; lane[3] = s[18]; lane[4] = s[19]; 224 s[15] ^= (~lane[1]) & lane[2]; 225 s[16] ^= (~lane[2]) & lane[3]; 226 s[17] ^= (~lane[3]) & lane[4]; 227 s[18] ^= (~lane[4]) & lane[0]; 228 s[19] ^= (~lane[0]) & lane[1]; 229 230 lane[0] = s[20]; lane[1] = s[21]; lane[2] = s[22]; lane[3] = s[23]; lane[4] = s[24]; 231 s[20] ^= (~lane[1]) & lane[2]; 232 s[21] ^= (~lane[2]) & lane[3]; 233 s[22] ^= (~lane[3]) & lane[4]; 234 s[23] ^= (~lane[4]) & lane[0]; 235 s[24] ^= (~lane[0]) & lane[1]; 236#endif 237 238 /* Iota */ 239 /* Decompress the round masks (see definition of rc) */ 240 s[0] ^= ((iota_r_packed[round] & 0x40ull) << 57 | 241 (iota_r_packed[round] & 0x20ull) << 26 | 242 (iota_r_packed[round] & 0x10ull) << 11 | 243 (iota_r_packed[round] & 0x8f)); 244 } 245} 246 247void mbedtls_sha3_init(mbedtls_sha3_context *ctx) 248{ 249 memset(ctx, 0, sizeof(mbedtls_sha3_context)); 250} 251 252void mbedtls_sha3_free(mbedtls_sha3_context *ctx) 253{ 254 if (ctx == NULL) { 255 return; 256 } 257 258 mbedtls_platform_zeroize(ctx, sizeof(mbedtls_sha3_context)); 259} 260 261void mbedtls_sha3_clone(mbedtls_sha3_context *dst, 262 const mbedtls_sha3_context *src) 263{ 264 *dst = *src; 265} 266 267/* 268 * SHA-3 context setup 269 */ 270int mbedtls_sha3_starts(mbedtls_sha3_context *ctx, mbedtls_sha3_id id) 271{ 272 switch (id) { 273 case MBEDTLS_SHA3_224: 274 ctx->olen = 224 / 8; 275 ctx->max_block_size = 1152 / 8; 276 break; 277 case MBEDTLS_SHA3_256: 278 ctx->olen = 256 / 8; 279 ctx->max_block_size = 1088 / 8; 280 break; 281 case MBEDTLS_SHA3_384: 282 ctx->olen = 384 / 8; 283 ctx->max_block_size = 832 / 8; 284 break; 285 case MBEDTLS_SHA3_512: 286 ctx->olen = 512 / 8; 287 ctx->max_block_size = 576 / 8; 288 break; 289 default: 290 return MBEDTLS_ERR_SHA3_BAD_INPUT_DATA; 291 } 292 293 memset(ctx->state, 0, sizeof(ctx->state)); 294 ctx->index = 0; 295 296 return 0; 297} 298 299/* 300 * SHA-3 process buffer 301 */ 302int mbedtls_sha3_update(mbedtls_sha3_context *ctx, 303 const uint8_t *input, 304 size_t ilen) 305{ 306 if (ilen >= 8) { 307 // 8-byte align index 308 int align_bytes = 8 - (ctx->index % 8); 309 if (align_bytes) { 310 for (; align_bytes > 0; align_bytes--) { 311 ABSORB(ctx, ctx->index, *input++); 312 ilen--; 313 ctx->index++; 314 } 315 if ((ctx->index = ctx->index % ctx->max_block_size) == 0) { 316 keccak_f1600(ctx); 317 } 318 } 319 320 // process input in 8-byte chunks 321 while (ilen >= 8) { 322 ABSORB(ctx, ctx->index, MBEDTLS_GET_UINT64_LE(input, 0)); 323 input += 8; 324 ilen -= 8; 325 if ((ctx->index = (ctx->index + 8) % ctx->max_block_size) == 0) { 326 keccak_f1600(ctx); 327 } 328 } 329 } 330 331 // handle remaining bytes 332 while (ilen-- > 0) { 333 ABSORB(ctx, ctx->index, *input++); 334 if ((ctx->index = (ctx->index + 1) % ctx->max_block_size) == 0) { 335 keccak_f1600(ctx); 336 } 337 } 338 339 return 0; 340} 341 342int mbedtls_sha3_finish(mbedtls_sha3_context *ctx, 343 uint8_t *output, size_t olen) 344{ 345 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED; 346 347 /* Catch SHA-3 families, with fixed output length */ 348 if (ctx->olen > 0) { 349 if (ctx->olen > olen) { 350 ret = MBEDTLS_ERR_SHA3_BAD_INPUT_DATA; 351 goto exit; 352 } 353 olen = ctx->olen; 354 } 355 356 ABSORB(ctx, ctx->index, XOR_BYTE); 357 ABSORB(ctx, ctx->max_block_size - 1, 0x80); 358 keccak_f1600(ctx); 359 ctx->index = 0; 360 361 while (olen-- > 0) { 362 *output++ = SQUEEZE(ctx, ctx->index); 363 364 if ((ctx->index = (ctx->index + 1) % ctx->max_block_size) == 0) { 365 keccak_f1600(ctx); 366 } 367 } 368 369 ret = 0; 370 371exit: 372 mbedtls_sha3_free(ctx); 373 return ret; 374} 375 376/* 377 * output = SHA-3( input buffer ) 378 */ 379int mbedtls_sha3(mbedtls_sha3_id id, const uint8_t *input, 380 size_t ilen, uint8_t *output, size_t olen) 381{ 382 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED; 383 mbedtls_sha3_context ctx; 384 385 mbedtls_sha3_init(&ctx); 386 387 /* Sanity checks are performed in every mbedtls_sha3_xxx() */ 388 if ((ret = mbedtls_sha3_starts(&ctx, id)) != 0) { 389 goto exit; 390 } 391 392 if ((ret = mbedtls_sha3_update(&ctx, input, ilen)) != 0) { 393 goto exit; 394 } 395 396 if ((ret = mbedtls_sha3_finish(&ctx, output, olen)) != 0) { 397 goto exit; 398 } 399 400exit: 401 mbedtls_sha3_free(&ctx); 402 403 return ret; 404} 405 406/**************** Self-tests ****************/ 407 408#if defined(MBEDTLS_SELF_TEST) 409 410static const unsigned char test_data[2][4] = 411{ 412 "", 413 "abc", 414}; 415 416static const size_t test_data_len[2] = 417{ 418 0, /* "" */ 419 3 /* "abc" */ 420}; 421 422static const unsigned char test_hash_sha3_224[2][28] = 423{ 424 { /* "" */ 425 0x6B, 0x4E, 0x03, 0x42, 0x36, 0x67, 0xDB, 0xB7, 426 0x3B, 0x6E, 0x15, 0x45, 0x4F, 0x0E, 0xB1, 0xAB, 427 0xD4, 0x59, 0x7F, 0x9A, 0x1B, 0x07, 0x8E, 0x3F, 428 0x5B, 0x5A, 0x6B, 0xC7 429 }, 430 { /* "abc" */ 431 0xE6, 0x42, 0x82, 0x4C, 0x3F, 0x8C, 0xF2, 0x4A, 432 0xD0, 0x92, 0x34, 0xEE, 0x7D, 0x3C, 0x76, 0x6F, 433 0xC9, 0xA3, 0xA5, 0x16, 0x8D, 0x0C, 0x94, 0xAD, 434 0x73, 0xB4, 0x6F, 0xDF 435 } 436}; 437 438static const unsigned char test_hash_sha3_256[2][32] = 439{ 440 { /* "" */ 441 0xA7, 0xFF, 0xC6, 0xF8, 0xBF, 0x1E, 0xD7, 0x66, 442 0x51, 0xC1, 0x47, 0x56, 0xA0, 0x61, 0xD6, 0x62, 443 0xF5, 0x80, 0xFF, 0x4D, 0xE4, 0x3B, 0x49, 0xFA, 444 0x82, 0xD8, 0x0A, 0x4B, 0x80, 0xF8, 0x43, 0x4A 445 }, 446 { /* "abc" */ 447 0x3A, 0x98, 0x5D, 0xA7, 0x4F, 0xE2, 0x25, 0xB2, 448 0x04, 0x5C, 0x17, 0x2D, 0x6B, 0xD3, 0x90, 0xBD, 449 0x85, 0x5F, 0x08, 0x6E, 0x3E, 0x9D, 0x52, 0x5B, 450 0x46, 0xBF, 0xE2, 0x45, 0x11, 0x43, 0x15, 0x32 451 } 452}; 453 454static const unsigned char test_hash_sha3_384[2][48] = 455{ 456 { /* "" */ 457 0x0C, 0x63, 0xA7, 0x5B, 0x84, 0x5E, 0x4F, 0x7D, 458 0x01, 0x10, 0x7D, 0x85, 0x2E, 0x4C, 0x24, 0x85, 459 0xC5, 0x1A, 0x50, 0xAA, 0xAA, 0x94, 0xFC, 0x61, 460 0x99, 0x5E, 0x71, 0xBB, 0xEE, 0x98, 0x3A, 0x2A, 461 0xC3, 0x71, 0x38, 0x31, 0x26, 0x4A, 0xDB, 0x47, 462 0xFB, 0x6B, 0xD1, 0xE0, 0x58, 0xD5, 0xF0, 0x04 463 }, 464 { /* "abc" */ 465 0xEC, 0x01, 0x49, 0x82, 0x88, 0x51, 0x6F, 0xC9, 466 0x26, 0x45, 0x9F, 0x58, 0xE2, 0xC6, 0xAD, 0x8D, 467 0xF9, 0xB4, 0x73, 0xCB, 0x0F, 0xC0, 0x8C, 0x25, 468 0x96, 0xDA, 0x7C, 0xF0, 0xE4, 0x9B, 0xE4, 0xB2, 469 0x98, 0xD8, 0x8C, 0xEA, 0x92, 0x7A, 0xC7, 0xF5, 470 0x39, 0xF1, 0xED, 0xF2, 0x28, 0x37, 0x6D, 0x25 471 } 472}; 473 474static const unsigned char test_hash_sha3_512[2][64] = 475{ 476 { /* "" */ 477 0xA6, 0x9F, 0x73, 0xCC, 0xA2, 0x3A, 0x9A, 0xC5, 478 0xC8, 0xB5, 0x67, 0xDC, 0x18, 0x5A, 0x75, 0x6E, 479 0x97, 0xC9, 0x82, 0x16, 0x4F, 0xE2, 0x58, 0x59, 480 0xE0, 0xD1, 0xDC, 0xC1, 0x47, 0x5C, 0x80, 0xA6, 481 0x15, 0xB2, 0x12, 0x3A, 0xF1, 0xF5, 0xF9, 0x4C, 482 0x11, 0xE3, 0xE9, 0x40, 0x2C, 0x3A, 0xC5, 0x58, 483 0xF5, 0x00, 0x19, 0x9D, 0x95, 0xB6, 0xD3, 0xE3, 484 0x01, 0x75, 0x85, 0x86, 0x28, 0x1D, 0xCD, 0x26 485 }, 486 { /* "abc" */ 487 0xB7, 0x51, 0x85, 0x0B, 0x1A, 0x57, 0x16, 0x8A, 488 0x56, 0x93, 0xCD, 0x92, 0x4B, 0x6B, 0x09, 0x6E, 489 0x08, 0xF6, 0x21, 0x82, 0x74, 0x44, 0xF7, 0x0D, 490 0x88, 0x4F, 0x5D, 0x02, 0x40, 0xD2, 0x71, 0x2E, 491 0x10, 0xE1, 0x16, 0xE9, 0x19, 0x2A, 0xF3, 0xC9, 492 0x1A, 0x7E, 0xC5, 0x76, 0x47, 0xE3, 0x93, 0x40, 493 0x57, 0x34, 0x0B, 0x4C, 0xF4, 0x08, 0xD5, 0xA5, 494 0x65, 0x92, 0xF8, 0x27, 0x4E, 0xEC, 0x53, 0xF0 495 } 496}; 497 498static const unsigned char long_kat_hash_sha3_224[28] = 499{ 500 0xD6, 0x93, 0x35, 0xB9, 0x33, 0x25, 0x19, 0x2E, 501 0x51, 0x6A, 0x91, 0x2E, 0x6D, 0x19, 0xA1, 0x5C, 502 0xB5, 0x1C, 0x6E, 0xD5, 0xC1, 0x52, 0x43, 0xE7, 503 0xA7, 0xFD, 0x65, 0x3C 504}; 505 506static const unsigned char long_kat_hash_sha3_256[32] = 507{ 508 0x5C, 0x88, 0x75, 0xAE, 0x47, 0x4A, 0x36, 0x34, 509 0xBA, 0x4F, 0xD5, 0x5E, 0xC8, 0x5B, 0xFF, 0xD6, 510 0x61, 0xF3, 0x2A, 0xCA, 0x75, 0xC6, 0xD6, 0x99, 511 0xD0, 0xCD, 0xCB, 0x6C, 0x11, 0x58, 0x91, 0xC1 512}; 513 514static const unsigned char long_kat_hash_sha3_384[48] = 515{ 516 0xEE, 0xE9, 0xE2, 0x4D, 0x78, 0xC1, 0x85, 0x53, 517 0x37, 0x98, 0x34, 0x51, 0xDF, 0x97, 0xC8, 0xAD, 518 0x9E, 0xED, 0xF2, 0x56, 0xC6, 0x33, 0x4F, 0x8E, 519 0x94, 0x8D, 0x25, 0x2D, 0x5E, 0x0E, 0x76, 0x84, 520 0x7A, 0xA0, 0x77, 0x4D, 0xDB, 0x90, 0xA8, 0x42, 521 0x19, 0x0D, 0x2C, 0x55, 0x8B, 0x4B, 0x83, 0x40 522}; 523 524static const unsigned char long_kat_hash_sha3_512[64] = 525{ 526 0x3C, 0x3A, 0x87, 0x6D, 0xA1, 0x40, 0x34, 0xAB, 527 0x60, 0x62, 0x7C, 0x07, 0x7B, 0xB9, 0x8F, 0x7E, 528 0x12, 0x0A, 0x2A, 0x53, 0x70, 0x21, 0x2D, 0xFF, 529 0xB3, 0x38, 0x5A, 0x18, 0xD4, 0xF3, 0x88, 0x59, 530 0xED, 0x31, 0x1D, 0x0A, 0x9D, 0x51, 0x41, 0xCE, 531 0x9C, 0xC5, 0xC6, 0x6E, 0xE6, 0x89, 0xB2, 0x66, 532 0xA8, 0xAA, 0x18, 0xAC, 0xE8, 0x28, 0x2A, 0x0E, 533 0x0D, 0xB5, 0x96, 0xC9, 0x0B, 0x0A, 0x7B, 0x87 534}; 535 536static int mbedtls_sha3_kat_test(int verbose, 537 const char *type_name, 538 mbedtls_sha3_id id, 539 int test_num) 540{ 541 uint8_t hash[64]; 542 int result; 543 544 result = mbedtls_sha3(id, 545 test_data[test_num], test_data_len[test_num], 546 hash, sizeof(hash)); 547 if (result != 0) { 548 if (verbose != 0) { 549 mbedtls_printf(" %s test %d error code: %d\n", 550 type_name, test_num, result); 551 } 552 553 return result; 554 } 555 556 switch (id) { 557 case MBEDTLS_SHA3_224: 558 result = memcmp(hash, test_hash_sha3_224[test_num], 28); 559 break; 560 case MBEDTLS_SHA3_256: 561 result = memcmp(hash, test_hash_sha3_256[test_num], 32); 562 break; 563 case MBEDTLS_SHA3_384: 564 result = memcmp(hash, test_hash_sha3_384[test_num], 48); 565 break; 566 case MBEDTLS_SHA3_512: 567 result = memcmp(hash, test_hash_sha3_512[test_num], 64); 568 break; 569 default: 570 break; 571 } 572 573 if (0 != result) { 574 if (verbose != 0) { 575 mbedtls_printf(" %s test %d failed\n", type_name, test_num); 576 } 577 578 return -1; 579 } 580 581 if (verbose != 0) { 582 mbedtls_printf(" %s test %d passed\n", type_name, test_num); 583 } 584 585 return 0; 586} 587 588static int mbedtls_sha3_long_kat_test(int verbose, 589 const char *type_name, 590 mbedtls_sha3_id id) 591{ 592 mbedtls_sha3_context ctx; 593 unsigned char buffer[1000]; 594 unsigned char hash[64]; 595 int result = 0; 596 597 memset(buffer, 'a', 1000); 598 599 if (verbose != 0) { 600 mbedtls_printf(" %s long KAT test ", type_name); 601 } 602 603 mbedtls_sha3_init(&ctx); 604 605 result = mbedtls_sha3_starts(&ctx, id); 606 if (result != 0) { 607 if (verbose != 0) { 608 mbedtls_printf("setup failed\n "); 609 } 610 } 611 612 /* Process 1,000,000 (one million) 'a' characters */ 613 for (int i = 0; i < 1000; i++) { 614 result = mbedtls_sha3_update(&ctx, buffer, 1000); 615 if (result != 0) { 616 if (verbose != 0) { 617 mbedtls_printf("update error code: %i\n", result); 618 } 619 620 goto cleanup; 621 } 622 } 623 624 result = mbedtls_sha3_finish(&ctx, hash, sizeof(hash)); 625 if (result != 0) { 626 if (verbose != 0) { 627 mbedtls_printf("finish error code: %d\n", result); 628 } 629 630 goto cleanup; 631 } 632 633 switch (id) { 634 case MBEDTLS_SHA3_224: 635 result = memcmp(hash, long_kat_hash_sha3_224, 28); 636 break; 637 case MBEDTLS_SHA3_256: 638 result = memcmp(hash, long_kat_hash_sha3_256, 32); 639 break; 640 case MBEDTLS_SHA3_384: 641 result = memcmp(hash, long_kat_hash_sha3_384, 48); 642 break; 643 case MBEDTLS_SHA3_512: 644 result = memcmp(hash, long_kat_hash_sha3_512, 64); 645 break; 646 default: 647 break; 648 } 649 650 if (result != 0) { 651 if (verbose != 0) { 652 mbedtls_printf("failed\n"); 653 } 654 } 655 656 if (verbose != 0) { 657 mbedtls_printf("passed\n"); 658 } 659 660cleanup: 661 mbedtls_sha3_free(&ctx); 662 return result; 663} 664 665int mbedtls_sha3_self_test(int verbose) 666{ 667 int i; 668 669 /* SHA-3 Known Answer Tests (KAT) */ 670 for (i = 0; i < 2; i++) { 671 if (0 != mbedtls_sha3_kat_test(verbose, 672 "SHA3-224", MBEDTLS_SHA3_224, i)) { 673 return 1; 674 } 675 676 if (0 != mbedtls_sha3_kat_test(verbose, 677 "SHA3-256", MBEDTLS_SHA3_256, i)) { 678 return 1; 679 } 680 681 if (0 != mbedtls_sha3_kat_test(verbose, 682 "SHA3-384", MBEDTLS_SHA3_384, i)) { 683 return 1; 684 } 685 686 if (0 != mbedtls_sha3_kat_test(verbose, 687 "SHA3-512", MBEDTLS_SHA3_512, i)) { 688 return 1; 689 } 690 } 691 692 /* SHA-3 long KAT tests */ 693 if (0 != mbedtls_sha3_long_kat_test(verbose, 694 "SHA3-224", MBEDTLS_SHA3_224)) { 695 return 1; 696 } 697 698 if (0 != mbedtls_sha3_long_kat_test(verbose, 699 "SHA3-256", MBEDTLS_SHA3_256)) { 700 return 1; 701 } 702 703 if (0 != mbedtls_sha3_long_kat_test(verbose, 704 "SHA3-384", MBEDTLS_SHA3_384)) { 705 return 1; 706 } 707 708 if (0 != mbedtls_sha3_long_kat_test(verbose, 709 "SHA3-512", MBEDTLS_SHA3_512)) { 710 return 1; 711 } 712 713 if (verbose != 0) { 714 mbedtls_printf("\n"); 715 } 716 717 return 0; 718} 719#endif /* MBEDTLS_SELF_TEST */ 720 721#endif /* MBEDTLS_SHA3_C */ 722