1 // SPDX-License-Identifier: Apache-2.0 2 /* 3 * FIPS-180-2 compliant SHA-384/512 implementation 4 * 5 * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved 6 * 7 * Licensed under the Apache License, Version 2.0 (the "License"); you may 8 * not use this file except in compliance with the License. 9 * You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, software 14 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 15 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 * See the License for the specific language governing permissions and 17 * limitations under the License. 18 * 19 * This file is part of mbed TLS (https://tls.mbed.org) 20 */ 21 /* 22 * The SHA-512 Secure Hash Standard was published by NIST in 2002. 23 * 24 * http://csrc.nist.gov/publications/fips/fips180-2/fips180-2.pdf 25 */ 26 27 #if !defined(MBEDTLS_CONFIG_FILE) 28 #include "mbedtls/config.h" 29 #else 30 #include MBEDTLS_CONFIG_FILE 31 #endif 32 33 #if defined(MBEDTLS_SHA512_C) 34 35 #include "mbedtls/sha512.h" 36 #include "mbedtls/platform_util.h" 37 38 #if defined(_MSC_VER) || defined(__WATCOMC__) 39 #define UL64(x) x##ui64 40 #else 41 #define UL64(x) x##ULL 42 #endif 43 44 #include <string.h> 45 46 #if defined(MBEDTLS_SELF_TEST) 47 #if defined(MBEDTLS_PLATFORM_C) 48 #include "mbedtls/platform.h" 49 #else 50 #include <stdio.h> 51 #include <stdlib.h> 52 #define mbedtls_printf printf 53 #define mbedtls_calloc calloc 54 #define mbedtls_free free 55 #endif /* MBEDTLS_PLATFORM_C */ 56 #endif /* MBEDTLS_SELF_TEST */ 57 58 #define SHA512_VALIDATE_RET(cond) \ 59 MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_SHA512_BAD_INPUT_DATA ) 60 #define SHA512_VALIDATE(cond) MBEDTLS_INTERNAL_VALIDATE( cond ) 61 62 #if !defined(MBEDTLS_SHA512_ALT) 63 64 /* 65 * 64-bit integer manipulation macros (big endian) 66 */ 67 #ifndef GET_UINT64_BE 68 #define GET_UINT64_BE(n,b,i) \ 69 { \ 70 (n) = ( (uint64_t) (b)[(i) ] << 56 ) \ 71 | ( (uint64_t) (b)[(i) + 1] << 48 ) \ 72 | ( (uint64_t) (b)[(i) + 2] << 40 ) \ 73 | ( (uint64_t) (b)[(i) + 3] << 32 ) \ 74 | ( (uint64_t) (b)[(i) + 4] << 24 ) \ 75 | ( (uint64_t) (b)[(i) + 5] << 16 ) \ 76 | ( (uint64_t) (b)[(i) + 6] << 8 ) \ 77 | ( (uint64_t) (b)[(i) + 7] ); \ 78 } 79 #endif /* GET_UINT64_BE */ 80 81 #ifndef PUT_UINT64_BE 82 #define PUT_UINT64_BE(n,b,i) \ 83 { \ 84 (b)[(i) ] = (unsigned char) ( (n) >> 56 ); \ 85 (b)[(i) + 1] = (unsigned char) ( (n) >> 48 ); \ 86 (b)[(i) + 2] = (unsigned char) ( (n) >> 40 ); \ 87 (b)[(i) + 3] = (unsigned char) ( (n) >> 32 ); \ 88 (b)[(i) + 4] = (unsigned char) ( (n) >> 24 ); \ 89 (b)[(i) + 5] = (unsigned char) ( (n) >> 16 ); \ 90 (b)[(i) + 6] = (unsigned char) ( (n) >> 8 ); \ 91 (b)[(i) + 7] = (unsigned char) ( (n) ); \ 92 } 93 #endif /* PUT_UINT64_BE */ 94 95 void mbedtls_sha512_init( mbedtls_sha512_context *ctx ) 96 { 97 SHA512_VALIDATE( ctx != NULL ); 98 99 memset( ctx, 0, sizeof( mbedtls_sha512_context ) ); 100 } 101 102 void mbedtls_sha512_free( mbedtls_sha512_context *ctx ) 103 { 104 if( ctx == NULL ) 105 return; 106 107 mbedtls_platform_zeroize( ctx, sizeof( mbedtls_sha512_context ) ); 108 } 109 110 void mbedtls_sha512_clone( mbedtls_sha512_context *dst, 111 const mbedtls_sha512_context *src ) 112 { 113 SHA512_VALIDATE( dst != NULL ); 114 SHA512_VALIDATE( src != NULL ); 115 116 *dst = *src; 117 } 118 119 /* 120 * SHA-512 context setup 121 */ 122 int mbedtls_sha512_starts_ret( mbedtls_sha512_context *ctx, int is384 ) 123 { 124 SHA512_VALIDATE_RET( ctx != NULL ); 125 SHA512_VALIDATE_RET( is384 == 0 || is384 == 1 ); 126 127 ctx->total[0] = 0; 128 ctx->total[1] = 0; 129 130 if( is384 == 0 ) 131 { 132 /* SHA-512 */ 133 ctx->state[0] = UL64(0x6A09E667F3BCC908); 134 ctx->state[1] = UL64(0xBB67AE8584CAA73B); 135 ctx->state[2] = UL64(0x3C6EF372FE94F82B); 136 ctx->state[3] = UL64(0xA54FF53A5F1D36F1); 137 ctx->state[4] = UL64(0x510E527FADE682D1); 138 ctx->state[5] = UL64(0x9B05688C2B3E6C1F); 139 ctx->state[6] = UL64(0x1F83D9ABFB41BD6B); 140 ctx->state[7] = UL64(0x5BE0CD19137E2179); 141 } 142 else 143 { 144 /* SHA-384 */ 145 ctx->state[0] = UL64(0xCBBB9D5DC1059ED8); 146 ctx->state[1] = UL64(0x629A292A367CD507); 147 ctx->state[2] = UL64(0x9159015A3070DD17); 148 ctx->state[3] = UL64(0x152FECD8F70E5939); 149 ctx->state[4] = UL64(0x67332667FFC00B31); 150 ctx->state[5] = UL64(0x8EB44A8768581511); 151 ctx->state[6] = UL64(0xDB0C2E0D64F98FA7); 152 ctx->state[7] = UL64(0x47B5481DBEFA4FA4); 153 } 154 155 ctx->is384 = is384; 156 157 return( 0 ); 158 } 159 160 #if !defined(MBEDTLS_DEPRECATED_REMOVED) 161 void mbedtls_sha512_starts( mbedtls_sha512_context *ctx, 162 int is384 ) 163 { 164 mbedtls_sha512_starts_ret( ctx, is384 ); 165 } 166 #endif 167 168 #if !defined(MBEDTLS_SHA512_PROCESS_ALT) 169 170 /* 171 * Round constants 172 */ 173 static const uint64_t K[80] = 174 { 175 UL64(0x428A2F98D728AE22), UL64(0x7137449123EF65CD), 176 UL64(0xB5C0FBCFEC4D3B2F), UL64(0xE9B5DBA58189DBBC), 177 UL64(0x3956C25BF348B538), UL64(0x59F111F1B605D019), 178 UL64(0x923F82A4AF194F9B), UL64(0xAB1C5ED5DA6D8118), 179 UL64(0xD807AA98A3030242), UL64(0x12835B0145706FBE), 180 UL64(0x243185BE4EE4B28C), UL64(0x550C7DC3D5FFB4E2), 181 UL64(0x72BE5D74F27B896F), UL64(0x80DEB1FE3B1696B1), 182 UL64(0x9BDC06A725C71235), UL64(0xC19BF174CF692694), 183 UL64(0xE49B69C19EF14AD2), UL64(0xEFBE4786384F25E3), 184 UL64(0x0FC19DC68B8CD5B5), UL64(0x240CA1CC77AC9C65), 185 UL64(0x2DE92C6F592B0275), UL64(0x4A7484AA6EA6E483), 186 UL64(0x5CB0A9DCBD41FBD4), UL64(0x76F988DA831153B5), 187 UL64(0x983E5152EE66DFAB), UL64(0xA831C66D2DB43210), 188 UL64(0xB00327C898FB213F), UL64(0xBF597FC7BEEF0EE4), 189 UL64(0xC6E00BF33DA88FC2), UL64(0xD5A79147930AA725), 190 UL64(0x06CA6351E003826F), UL64(0x142929670A0E6E70), 191 UL64(0x27B70A8546D22FFC), UL64(0x2E1B21385C26C926), 192 UL64(0x4D2C6DFC5AC42AED), UL64(0x53380D139D95B3DF), 193 UL64(0x650A73548BAF63DE), UL64(0x766A0ABB3C77B2A8), 194 UL64(0x81C2C92E47EDAEE6), UL64(0x92722C851482353B), 195 UL64(0xA2BFE8A14CF10364), UL64(0xA81A664BBC423001), 196 UL64(0xC24B8B70D0F89791), UL64(0xC76C51A30654BE30), 197 UL64(0xD192E819D6EF5218), UL64(0xD69906245565A910), 198 UL64(0xF40E35855771202A), UL64(0x106AA07032BBD1B8), 199 UL64(0x19A4C116B8D2D0C8), UL64(0x1E376C085141AB53), 200 UL64(0x2748774CDF8EEB99), UL64(0x34B0BCB5E19B48A8), 201 UL64(0x391C0CB3C5C95A63), UL64(0x4ED8AA4AE3418ACB), 202 UL64(0x5B9CCA4F7763E373), UL64(0x682E6FF3D6B2B8A3), 203 UL64(0x748F82EE5DEFB2FC), UL64(0x78A5636F43172F60), 204 UL64(0x84C87814A1F0AB72), UL64(0x8CC702081A6439EC), 205 UL64(0x90BEFFFA23631E28), UL64(0xA4506CEBDE82BDE9), 206 UL64(0xBEF9A3F7B2C67915), UL64(0xC67178F2E372532B), 207 UL64(0xCA273ECEEA26619C), UL64(0xD186B8C721C0C207), 208 UL64(0xEADA7DD6CDE0EB1E), UL64(0xF57D4F7FEE6ED178), 209 UL64(0x06F067AA72176FBA), UL64(0x0A637DC5A2C898A6), 210 UL64(0x113F9804BEF90DAE), UL64(0x1B710B35131C471B), 211 UL64(0x28DB77F523047D84), UL64(0x32CAAB7B40C72493), 212 UL64(0x3C9EBE0A15C9BEBC), UL64(0x431D67C49C100D4C), 213 UL64(0x4CC5D4BECB3E42B6), UL64(0x597F299CFC657E2A), 214 UL64(0x5FCB6FAB3AD6FAEC), UL64(0x6C44198C4A475817) 215 }; 216 217 int mbedtls_internal_sha512_process( mbedtls_sha512_context *ctx, 218 const unsigned char data[128] ) 219 { 220 int i; 221 uint64_t temp1, temp2, W[80]; 222 uint64_t A, B, C, D, E, F, G, H; 223 224 SHA512_VALIDATE_RET( ctx != NULL ); 225 SHA512_VALIDATE_RET( (const unsigned char *)data != NULL ); 226 227 #define SHR(x,n) ((x) >> (n)) 228 #define ROTR(x,n) (SHR((x),(n)) | ((x) << (64 - (n)))) 229 230 #define S0(x) (ROTR(x, 1) ^ ROTR(x, 8) ^ SHR(x, 7)) 231 #define S1(x) (ROTR(x,19) ^ ROTR(x,61) ^ SHR(x, 6)) 232 233 #define S2(x) (ROTR(x,28) ^ ROTR(x,34) ^ ROTR(x,39)) 234 #define S3(x) (ROTR(x,14) ^ ROTR(x,18) ^ ROTR(x,41)) 235 236 #define F0(x,y,z) (((x) & (y)) | ((z) & ((x) | (y)))) 237 #define F1(x,y,z) ((z) ^ ((x) & ((y) ^ (z)))) 238 239 #define P(a,b,c,d,e,f,g,h,x,K) \ 240 do \ 241 { \ 242 temp1 = (h) + S3(e) + F1((e),(f),(g)) + (K) + (x); \ 243 temp2 = S2(a) + F0((a),(b),(c)); \ 244 (d) += temp1; (h) = temp1 + temp2; \ 245 } while( 0 ) 246 247 for( i = 0; i < 16; i++ ) 248 { 249 GET_UINT64_BE( W[i], data, i << 3 ); 250 } 251 252 for( ; i < 80; i++ ) 253 { 254 W[i] = S1(W[i - 2]) + W[i - 7] + 255 S0(W[i - 15]) + W[i - 16]; 256 } 257 258 A = ctx->state[0]; 259 B = ctx->state[1]; 260 C = ctx->state[2]; 261 D = ctx->state[3]; 262 E = ctx->state[4]; 263 F = ctx->state[5]; 264 G = ctx->state[6]; 265 H = ctx->state[7]; 266 i = 0; 267 268 do 269 { 270 P( A, B, C, D, E, F, G, H, W[i], K[i] ); i++; 271 P( H, A, B, C, D, E, F, G, W[i], K[i] ); i++; 272 P( G, H, A, B, C, D, E, F, W[i], K[i] ); i++; 273 P( F, G, H, A, B, C, D, E, W[i], K[i] ); i++; 274 P( E, F, G, H, A, B, C, D, W[i], K[i] ); i++; 275 P( D, E, F, G, H, A, B, C, W[i], K[i] ); i++; 276 P( C, D, E, F, G, H, A, B, W[i], K[i] ); i++; 277 P( B, C, D, E, F, G, H, A, W[i], K[i] ); i++; 278 } 279 while( i < 80 ); 280 281 ctx->state[0] += A; 282 ctx->state[1] += B; 283 ctx->state[2] += C; 284 ctx->state[3] += D; 285 ctx->state[4] += E; 286 ctx->state[5] += F; 287 ctx->state[6] += G; 288 ctx->state[7] += H; 289 290 return( 0 ); 291 } 292 293 #if !defined(MBEDTLS_DEPRECATED_REMOVED) 294 void mbedtls_sha512_process( mbedtls_sha512_context *ctx, 295 const unsigned char data[128] ) 296 { 297 mbedtls_internal_sha512_process( ctx, data ); 298 } 299 #endif 300 #endif /* !MBEDTLS_SHA512_PROCESS_ALT */ 301 302 /* 303 * SHA-512 process buffer 304 */ 305 int mbedtls_sha512_update_ret( mbedtls_sha512_context *ctx, 306 const unsigned char *input, 307 size_t ilen ) 308 { 309 int ret; 310 size_t fill; 311 unsigned int left; 312 313 SHA512_VALIDATE_RET( ctx != NULL ); 314 SHA512_VALIDATE_RET( ilen == 0 || input != NULL ); 315 316 if( ilen == 0 ) 317 return( 0 ); 318 319 left = (unsigned int) (ctx->total[0] & 0x7F); 320 fill = 128 - left; 321 322 ctx->total[0] += (uint64_t) ilen; 323 324 if( ctx->total[0] < (uint64_t) ilen ) 325 ctx->total[1]++; 326 327 if( left && ilen >= fill ) 328 { 329 memcpy( (void *) (ctx->buffer + left), input, fill ); 330 331 if( ( ret = mbedtls_internal_sha512_process( ctx, ctx->buffer ) ) != 0 ) 332 return( ret ); 333 334 input += fill; 335 ilen -= fill; 336 left = 0; 337 } 338 339 while( ilen >= 128 ) 340 { 341 if( ( ret = mbedtls_internal_sha512_process( ctx, input ) ) != 0 ) 342 return( ret ); 343 344 input += 128; 345 ilen -= 128; 346 } 347 348 if( ilen > 0 ) 349 memcpy( (void *) (ctx->buffer + left), input, ilen ); 350 351 return( 0 ); 352 } 353 354 #if !defined(MBEDTLS_DEPRECATED_REMOVED) 355 void mbedtls_sha512_update( mbedtls_sha512_context *ctx, 356 const unsigned char *input, 357 size_t ilen ) 358 { 359 mbedtls_sha512_update_ret( ctx, input, ilen ); 360 } 361 #endif 362 363 /* 364 * SHA-512 final digest 365 */ 366 int mbedtls_sha512_finish_ret( mbedtls_sha512_context *ctx, 367 unsigned char output[64] ) 368 { 369 int ret; 370 unsigned used; 371 uint64_t high, low; 372 373 SHA512_VALIDATE_RET( ctx != NULL ); 374 SHA512_VALIDATE_RET( (unsigned char *)output != NULL ); 375 376 /* 377 * Add padding: 0x80 then 0x00 until 16 bytes remain for the length 378 */ 379 used = ctx->total[0] & 0x7F; 380 381 ctx->buffer[used++] = 0x80; 382 383 if( used <= 112 ) 384 { 385 /* Enough room for padding + length in current block */ 386 memset( ctx->buffer + used, 0, 112 - used ); 387 } 388 else 389 { 390 /* We'll need an extra block */ 391 memset( ctx->buffer + used, 0, 128 - used ); 392 393 if( ( ret = mbedtls_internal_sha512_process( ctx, ctx->buffer ) ) != 0 ) 394 return( ret ); 395 396 memset( ctx->buffer, 0, 112 ); 397 } 398 399 /* 400 * Add message length 401 */ 402 high = ( ctx->total[0] >> 61 ) 403 | ( ctx->total[1] << 3 ); 404 low = ( ctx->total[0] << 3 ); 405 406 PUT_UINT64_BE( high, ctx->buffer, 112 ); 407 PUT_UINT64_BE( low, ctx->buffer, 120 ); 408 409 if( ( ret = mbedtls_internal_sha512_process( ctx, ctx->buffer ) ) != 0 ) 410 return( ret ); 411 412 /* 413 * Output final state 414 */ 415 PUT_UINT64_BE( ctx->state[0], output, 0 ); 416 PUT_UINT64_BE( ctx->state[1], output, 8 ); 417 PUT_UINT64_BE( ctx->state[2], output, 16 ); 418 PUT_UINT64_BE( ctx->state[3], output, 24 ); 419 PUT_UINT64_BE( ctx->state[4], output, 32 ); 420 PUT_UINT64_BE( ctx->state[5], output, 40 ); 421 422 if( ctx->is384 == 0 ) 423 { 424 PUT_UINT64_BE( ctx->state[6], output, 48 ); 425 PUT_UINT64_BE( ctx->state[7], output, 56 ); 426 } 427 428 return( 0 ); 429 } 430 431 #if !defined(MBEDTLS_DEPRECATED_REMOVED) 432 void mbedtls_sha512_finish( mbedtls_sha512_context *ctx, 433 unsigned char output[64] ) 434 { 435 mbedtls_sha512_finish_ret( ctx, output ); 436 } 437 #endif 438 439 #endif /* !MBEDTLS_SHA512_ALT */ 440 441 /* 442 * output = SHA-512( input buffer ) 443 */ 444 int mbedtls_sha512_ret( const unsigned char *input, 445 size_t ilen, 446 unsigned char output[64], 447 int is384 ) 448 { 449 int ret; 450 mbedtls_sha512_context ctx; 451 452 SHA512_VALIDATE_RET( is384 == 0 || is384 == 1 ); 453 SHA512_VALIDATE_RET( ilen == 0 || input != NULL ); 454 SHA512_VALIDATE_RET( (unsigned char *)output != NULL ); 455 456 mbedtls_sha512_init( &ctx ); 457 458 if( ( ret = mbedtls_sha512_starts_ret( &ctx, is384 ) ) != 0 ) 459 goto exit; 460 461 if( ( ret = mbedtls_sha512_update_ret( &ctx, input, ilen ) ) != 0 ) 462 goto exit; 463 464 if( ( ret = mbedtls_sha512_finish_ret( &ctx, output ) ) != 0 ) 465 goto exit; 466 467 exit: 468 mbedtls_sha512_free( &ctx ); 469 470 return( ret ); 471 } 472 473 #if !defined(MBEDTLS_DEPRECATED_REMOVED) 474 void mbedtls_sha512( const unsigned char *input, 475 size_t ilen, 476 unsigned char output[64], 477 int is384 ) 478 { 479 mbedtls_sha512_ret( input, ilen, output, is384 ); 480 } 481 #endif 482 483 #if defined(MBEDTLS_SELF_TEST) 484 485 /* 486 * FIPS-180-2 test vectors 487 */ 488 static const unsigned char sha512_test_buf[3][113] = 489 { 490 { "abc" }, 491 { "abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmn" 492 "hijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu" }, 493 { "" } 494 }; 495 496 static const size_t sha512_test_buflen[3] = 497 { 498 3, 112, 1000 499 }; 500 501 static const unsigned char sha512_test_sum[6][64] = 502 { 503 /* 504 * SHA-384 test vectors 505 */ 506 { 0xCB, 0x00, 0x75, 0x3F, 0x45, 0xA3, 0x5E, 0x8B, 507 0xB5, 0xA0, 0x3D, 0x69, 0x9A, 0xC6, 0x50, 0x07, 508 0x27, 0x2C, 0x32, 0xAB, 0x0E, 0xDE, 0xD1, 0x63, 509 0x1A, 0x8B, 0x60, 0x5A, 0x43, 0xFF, 0x5B, 0xED, 510 0x80, 0x86, 0x07, 0x2B, 0xA1, 0xE7, 0xCC, 0x23, 511 0x58, 0xBA, 0xEC, 0xA1, 0x34, 0xC8, 0x25, 0xA7 }, 512 { 0x09, 0x33, 0x0C, 0x33, 0xF7, 0x11, 0x47, 0xE8, 513 0x3D, 0x19, 0x2F, 0xC7, 0x82, 0xCD, 0x1B, 0x47, 514 0x53, 0x11, 0x1B, 0x17, 0x3B, 0x3B, 0x05, 0xD2, 515 0x2F, 0xA0, 0x80, 0x86, 0xE3, 0xB0, 0xF7, 0x12, 516 0xFC, 0xC7, 0xC7, 0x1A, 0x55, 0x7E, 0x2D, 0xB9, 517 0x66, 0xC3, 0xE9, 0xFA, 0x91, 0x74, 0x60, 0x39 }, 518 { 0x9D, 0x0E, 0x18, 0x09, 0x71, 0x64, 0x74, 0xCB, 519 0x08, 0x6E, 0x83, 0x4E, 0x31, 0x0A, 0x4A, 0x1C, 520 0xED, 0x14, 0x9E, 0x9C, 0x00, 0xF2, 0x48, 0x52, 521 0x79, 0x72, 0xCE, 0xC5, 0x70, 0x4C, 0x2A, 0x5B, 522 0x07, 0xB8, 0xB3, 0xDC, 0x38, 0xEC, 0xC4, 0xEB, 523 0xAE, 0x97, 0xDD, 0xD8, 0x7F, 0x3D, 0x89, 0x85 }, 524 525 /* 526 * SHA-512 test vectors 527 */ 528 { 0xDD, 0xAF, 0x35, 0xA1, 0x93, 0x61, 0x7A, 0xBA, 529 0xCC, 0x41, 0x73, 0x49, 0xAE, 0x20, 0x41, 0x31, 530 0x12, 0xE6, 0xFA, 0x4E, 0x89, 0xA9, 0x7E, 0xA2, 531 0x0A, 0x9E, 0xEE, 0xE6, 0x4B, 0x55, 0xD3, 0x9A, 532 0x21, 0x92, 0x99, 0x2A, 0x27, 0x4F, 0xC1, 0xA8, 533 0x36, 0xBA, 0x3C, 0x23, 0xA3, 0xFE, 0xEB, 0xBD, 534 0x45, 0x4D, 0x44, 0x23, 0x64, 0x3C, 0xE8, 0x0E, 535 0x2A, 0x9A, 0xC9, 0x4F, 0xA5, 0x4C, 0xA4, 0x9F }, 536 { 0x8E, 0x95, 0x9B, 0x75, 0xDA, 0xE3, 0x13, 0xDA, 537 0x8C, 0xF4, 0xF7, 0x28, 0x14, 0xFC, 0x14, 0x3F, 538 0x8F, 0x77, 0x79, 0xC6, 0xEB, 0x9F, 0x7F, 0xA1, 539 0x72, 0x99, 0xAE, 0xAD, 0xB6, 0x88, 0x90, 0x18, 540 0x50, 0x1D, 0x28, 0x9E, 0x49, 0x00, 0xF7, 0xE4, 541 0x33, 0x1B, 0x99, 0xDE, 0xC4, 0xB5, 0x43, 0x3A, 542 0xC7, 0xD3, 0x29, 0xEE, 0xB6, 0xDD, 0x26, 0x54, 543 0x5E, 0x96, 0xE5, 0x5B, 0x87, 0x4B, 0xE9, 0x09 }, 544 { 0xE7, 0x18, 0x48, 0x3D, 0x0C, 0xE7, 0x69, 0x64, 545 0x4E, 0x2E, 0x42, 0xC7, 0xBC, 0x15, 0xB4, 0x63, 546 0x8E, 0x1F, 0x98, 0xB1, 0x3B, 0x20, 0x44, 0x28, 547 0x56, 0x32, 0xA8, 0x03, 0xAF, 0xA9, 0x73, 0xEB, 548 0xDE, 0x0F, 0xF2, 0x44, 0x87, 0x7E, 0xA6, 0x0A, 549 0x4C, 0xB0, 0x43, 0x2C, 0xE5, 0x77, 0xC3, 0x1B, 550 0xEB, 0x00, 0x9C, 0x5C, 0x2C, 0x49, 0xAA, 0x2E, 551 0x4E, 0xAD, 0xB2, 0x17, 0xAD, 0x8C, 0xC0, 0x9B } 552 }; 553 554 /* 555 * Checkup routine 556 */ 557 int mbedtls_sha512_self_test( int verbose ) 558 { 559 int i, j, k, buflen, ret = 0; 560 unsigned char *buf; 561 unsigned char sha512sum[64]; 562 mbedtls_sha512_context ctx; 563 564 buf = mbedtls_calloc( 1024, sizeof(unsigned char) ); 565 if( NULL == buf ) 566 { 567 if( verbose != 0 ) 568 mbedtls_printf( "Buffer allocation failed\n" ); 569 570 return( 1 ); 571 } 572 573 mbedtls_sha512_init( &ctx ); 574 575 for( i = 0; i < 6; i++ ) 576 { 577 j = i % 3; 578 k = i < 3; 579 580 if( verbose != 0 ) 581 mbedtls_printf( " SHA-%d test #%d: ", 512 - k * 128, j + 1 ); 582 583 if( ( ret = mbedtls_sha512_starts_ret( &ctx, k ) ) != 0 ) 584 goto fail; 585 586 if( j == 2 ) 587 { 588 memset( buf, 'a', buflen = 1000 ); 589 590 for( j = 0; j < 1000; j++ ) 591 { 592 ret = mbedtls_sha512_update_ret( &ctx, buf, buflen ); 593 if( ret != 0 ) 594 goto fail; 595 } 596 } 597 else 598 { 599 ret = mbedtls_sha512_update_ret( &ctx, sha512_test_buf[j], 600 sha512_test_buflen[j] ); 601 if( ret != 0 ) 602 goto fail; 603 } 604 605 if( ( ret = mbedtls_sha512_finish_ret( &ctx, sha512sum ) ) != 0 ) 606 goto fail; 607 608 if( memcmp( sha512sum, sha512_test_sum[i], 64 - k * 16 ) != 0 ) 609 { 610 ret = 1; 611 goto fail; 612 } 613 614 if( verbose != 0 ) 615 mbedtls_printf( "passed\n" ); 616 } 617 618 if( verbose != 0 ) 619 mbedtls_printf( "\n" ); 620 621 goto exit; 622 623 fail: 624 if( verbose != 0 ) 625 mbedtls_printf( "failed\n" ); 626 627 exit: 628 mbedtls_sha512_free( &ctx ); 629 mbedtls_free( buf ); 630 631 return( ret ); 632 } 633 634 #endif /* MBEDTLS_SELF_TEST */ 635 636 #endif /* MBEDTLS_SHA512_C */ 637