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