blob: f62a58dc9870412aba5d8a7a753b6e88af8d6d25 [file] [log] [blame]
Paul Bakker5121ce52009-01-03 21:22:43 +00001/*
2 * FIPS-180-2 compliant SHA-384/512 implementation
3 *
Manuel Pégourié-Gonnard6fb81872015-07-27 11:11:48 +02004 * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved
Manuel Pégourié-Gonnard37ff1402015-09-04 14:21:07 +02005 * SPDX-License-Identifier: Apache-2.0
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.
Paul Bakkerb96f1542010-07-18 20:36:00 +000018 *
Manuel Pégourié-Gonnardfe446432015-03-06 13:17:10 +000019 * This file is part of mbed TLS (https://tls.mbed.org)
Paul Bakker5121ce52009-01-03 21:22:43 +000020 */
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
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020027#if !defined(MBEDTLS_CONFIG_FILE)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000028#include "mbedtls/config.h"
Manuel Pégourié-Gonnardcef4ad22014-04-29 12:39:06 +020029#else
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020030#include MBEDTLS_CONFIG_FILE
Manuel Pégourié-Gonnardcef4ad22014-04-29 12:39:06 +020031#endif
Paul Bakker5121ce52009-01-03 21:22:43 +000032
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020033#if defined(MBEDTLS_SHA512_C)
Paul Bakker5121ce52009-01-03 21:22:43 +000034
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000035#include "mbedtls/sha512.h"
Paul Bakker5121ce52009-01-03 21:22:43 +000036
Manuel Pégourié-Gonnard1dd16742015-03-05 16:13:04 +000037#if defined(_MSC_VER) || defined(__WATCOMC__)
38 #define UL64(x) x##ui64
39#else
40 #define UL64(x) x##ULL
41#endif
42
Rich Evans00ab4702015-02-06 13:43:58 +000043#include <string.h>
44
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020045#if defined(MBEDTLS_SELF_TEST)
46#if defined(MBEDTLS_PLATFORM_C)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000047#include "mbedtls/platform.h"
Paul Bakker7dc4c442014-02-01 22:50:26 +010048#else
Rich Evans00ab4702015-02-06 13:43:58 +000049#include <stdio.h>
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020050#define mbedtls_printf printf
51#endif /* MBEDTLS_PLATFORM_C */
52#endif /* MBEDTLS_SELF_TEST */
Paul Bakker7dc4c442014-02-01 22:50:26 +010053
Manuel Pégourié-Gonnard8b2641d2015-08-27 20:03:46 +020054#if !defined(MBEDTLS_SHA512_ALT)
55
Paul Bakker34617722014-06-13 17:20:13 +020056/* Implementation that should never be optimized out by the compiler */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020057static void mbedtls_zeroize( void *v, size_t n ) {
Paul Bakker34617722014-06-13 17:20:13 +020058 volatile unsigned char *p = v; while( n-- ) *p++ = 0;
59}
60
Paul Bakker5121ce52009-01-03 21:22:43 +000061/*
62 * 64-bit integer manipulation macros (big endian)
63 */
64#ifndef GET_UINT64_BE
65#define GET_UINT64_BE(n,b,i) \
66{ \
Paul Bakker5c2364c2012-10-01 14:41:15 +000067 (n) = ( (uint64_t) (b)[(i) ] << 56 ) \
68 | ( (uint64_t) (b)[(i) + 1] << 48 ) \
69 | ( (uint64_t) (b)[(i) + 2] << 40 ) \
70 | ( (uint64_t) (b)[(i) + 3] << 32 ) \
71 | ( (uint64_t) (b)[(i) + 4] << 24 ) \
72 | ( (uint64_t) (b)[(i) + 5] << 16 ) \
73 | ( (uint64_t) (b)[(i) + 6] << 8 ) \
74 | ( (uint64_t) (b)[(i) + 7] ); \
Paul Bakker5121ce52009-01-03 21:22:43 +000075}
Paul Bakker9af723c2014-05-01 13:03:14 +020076#endif /* GET_UINT64_BE */
Paul Bakker5121ce52009-01-03 21:22:43 +000077
78#ifndef PUT_UINT64_BE
79#define PUT_UINT64_BE(n,b,i) \
80{ \
81 (b)[(i) ] = (unsigned char) ( (n) >> 56 ); \
82 (b)[(i) + 1] = (unsigned char) ( (n) >> 48 ); \
83 (b)[(i) + 2] = (unsigned char) ( (n) >> 40 ); \
84 (b)[(i) + 3] = (unsigned char) ( (n) >> 32 ); \
85 (b)[(i) + 4] = (unsigned char) ( (n) >> 24 ); \
86 (b)[(i) + 5] = (unsigned char) ( (n) >> 16 ); \
87 (b)[(i) + 6] = (unsigned char) ( (n) >> 8 ); \
88 (b)[(i) + 7] = (unsigned char) ( (n) ); \
89}
Paul Bakker9af723c2014-05-01 13:03:14 +020090#endif /* PUT_UINT64_BE */
Paul Bakker5121ce52009-01-03 21:22:43 +000091
92/*
93 * Round constants
94 */
Paul Bakker5c2364c2012-10-01 14:41:15 +000095static const uint64_t K[80] =
Paul Bakker5121ce52009-01-03 21:22:43 +000096{
97 UL64(0x428A2F98D728AE22), UL64(0x7137449123EF65CD),
98 UL64(0xB5C0FBCFEC4D3B2F), UL64(0xE9B5DBA58189DBBC),
99 UL64(0x3956C25BF348B538), UL64(0x59F111F1B605D019),
100 UL64(0x923F82A4AF194F9B), UL64(0xAB1C5ED5DA6D8118),
101 UL64(0xD807AA98A3030242), UL64(0x12835B0145706FBE),
102 UL64(0x243185BE4EE4B28C), UL64(0x550C7DC3D5FFB4E2),
103 UL64(0x72BE5D74F27B896F), UL64(0x80DEB1FE3B1696B1),
104 UL64(0x9BDC06A725C71235), UL64(0xC19BF174CF692694),
105 UL64(0xE49B69C19EF14AD2), UL64(0xEFBE4786384F25E3),
106 UL64(0x0FC19DC68B8CD5B5), UL64(0x240CA1CC77AC9C65),
107 UL64(0x2DE92C6F592B0275), UL64(0x4A7484AA6EA6E483),
108 UL64(0x5CB0A9DCBD41FBD4), UL64(0x76F988DA831153B5),
109 UL64(0x983E5152EE66DFAB), UL64(0xA831C66D2DB43210),
110 UL64(0xB00327C898FB213F), UL64(0xBF597FC7BEEF0EE4),
111 UL64(0xC6E00BF33DA88FC2), UL64(0xD5A79147930AA725),
112 UL64(0x06CA6351E003826F), UL64(0x142929670A0E6E70),
113 UL64(0x27B70A8546D22FFC), UL64(0x2E1B21385C26C926),
114 UL64(0x4D2C6DFC5AC42AED), UL64(0x53380D139D95B3DF),
115 UL64(0x650A73548BAF63DE), UL64(0x766A0ABB3C77B2A8),
116 UL64(0x81C2C92E47EDAEE6), UL64(0x92722C851482353B),
117 UL64(0xA2BFE8A14CF10364), UL64(0xA81A664BBC423001),
118 UL64(0xC24B8B70D0F89791), UL64(0xC76C51A30654BE30),
119 UL64(0xD192E819D6EF5218), UL64(0xD69906245565A910),
120 UL64(0xF40E35855771202A), UL64(0x106AA07032BBD1B8),
121 UL64(0x19A4C116B8D2D0C8), UL64(0x1E376C085141AB53),
122 UL64(0x2748774CDF8EEB99), UL64(0x34B0BCB5E19B48A8),
123 UL64(0x391C0CB3C5C95A63), UL64(0x4ED8AA4AE3418ACB),
124 UL64(0x5B9CCA4F7763E373), UL64(0x682E6FF3D6B2B8A3),
125 UL64(0x748F82EE5DEFB2FC), UL64(0x78A5636F43172F60),
126 UL64(0x84C87814A1F0AB72), UL64(0x8CC702081A6439EC),
127 UL64(0x90BEFFFA23631E28), UL64(0xA4506CEBDE82BDE9),
128 UL64(0xBEF9A3F7B2C67915), UL64(0xC67178F2E372532B),
129 UL64(0xCA273ECEEA26619C), UL64(0xD186B8C721C0C207),
130 UL64(0xEADA7DD6CDE0EB1E), UL64(0xF57D4F7FEE6ED178),
131 UL64(0x06F067AA72176FBA), UL64(0x0A637DC5A2C898A6),
132 UL64(0x113F9804BEF90DAE), UL64(0x1B710B35131C471B),
133 UL64(0x28DB77F523047D84), UL64(0x32CAAB7B40C72493),
134 UL64(0x3C9EBE0A15C9BEBC), UL64(0x431D67C49C100D4C),
135 UL64(0x4CC5D4BECB3E42B6), UL64(0x597F299CFC657E2A),
136 UL64(0x5FCB6FAB3AD6FAEC), UL64(0x6C44198C4A475817)
137};
138
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200139void mbedtls_sha512_init( mbedtls_sha512_context *ctx )
Paul Bakker5b4af392014-06-26 12:09:34 +0200140{
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200141 memset( ctx, 0, sizeof( mbedtls_sha512_context ) );
Paul Bakker5b4af392014-06-26 12:09:34 +0200142}
143
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200144void mbedtls_sha512_free( mbedtls_sha512_context *ctx )
Paul Bakker5b4af392014-06-26 12:09:34 +0200145{
146 if( ctx == NULL )
147 return;
148
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200149 mbedtls_zeroize( ctx, sizeof( mbedtls_sha512_context ) );
Paul Bakker5b4af392014-06-26 12:09:34 +0200150}
151
Manuel Pégourié-Gonnard16d412f2015-07-06 15:26:26 +0200152void mbedtls_sha512_clone( mbedtls_sha512_context *dst,
153 const mbedtls_sha512_context *src )
154{
155 *dst = *src;
156}
157
Paul Bakker5121ce52009-01-03 21:22:43 +0000158/*
159 * SHA-512 context setup
160 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200161void mbedtls_sha512_starts( mbedtls_sha512_context *ctx, int is384 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000162{
163 ctx->total[0] = 0;
164 ctx->total[1] = 0;
165
166 if( is384 == 0 )
167 {
168 /* SHA-512 */
169 ctx->state[0] = UL64(0x6A09E667F3BCC908);
170 ctx->state[1] = UL64(0xBB67AE8584CAA73B);
171 ctx->state[2] = UL64(0x3C6EF372FE94F82B);
172 ctx->state[3] = UL64(0xA54FF53A5F1D36F1);
173 ctx->state[4] = UL64(0x510E527FADE682D1);
174 ctx->state[5] = UL64(0x9B05688C2B3E6C1F);
175 ctx->state[6] = UL64(0x1F83D9ABFB41BD6B);
176 ctx->state[7] = UL64(0x5BE0CD19137E2179);
177 }
178 else
179 {
180 /* SHA-384 */
181 ctx->state[0] = UL64(0xCBBB9D5DC1059ED8);
182 ctx->state[1] = UL64(0x629A292A367CD507);
183 ctx->state[2] = UL64(0x9159015A3070DD17);
184 ctx->state[3] = UL64(0x152FECD8F70E5939);
185 ctx->state[4] = UL64(0x67332667FFC00B31);
186 ctx->state[5] = UL64(0x8EB44A8768581511);
187 ctx->state[6] = UL64(0xDB0C2E0D64F98FA7);
188 ctx->state[7] = UL64(0x47B5481DBEFA4FA4);
189 }
190
191 ctx->is384 = is384;
192}
193
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200194#if !defined(MBEDTLS_SHA512_PROCESS_ALT)
195void mbedtls_sha512_process( mbedtls_sha512_context *ctx, const unsigned char data[128] )
Paul Bakker5121ce52009-01-03 21:22:43 +0000196{
197 int i;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000198 uint64_t temp1, temp2, W[80];
199 uint64_t A, B, C, D, E, F, G, H;
Paul Bakker5121ce52009-01-03 21:22:43 +0000200
201#define SHR(x,n) (x >> n)
202#define ROTR(x,n) (SHR(x,n) | (x << (64 - n)))
203
204#define S0(x) (ROTR(x, 1) ^ ROTR(x, 8) ^ SHR(x, 7))
205#define S1(x) (ROTR(x,19) ^ ROTR(x,61) ^ SHR(x, 6))
206
207#define S2(x) (ROTR(x,28) ^ ROTR(x,34) ^ ROTR(x,39))
208#define S3(x) (ROTR(x,14) ^ ROTR(x,18) ^ ROTR(x,41))
209
210#define F0(x,y,z) ((x & y) | (z & (x | y)))
211#define F1(x,y,z) (z ^ (x & (y ^ z)))
212
213#define P(a,b,c,d,e,f,g,h,x,K) \
214{ \
215 temp1 = h + S3(e) + F1(e,f,g) + K + x; \
216 temp2 = S2(a) + F0(a,b,c); \
217 d += temp1; h = temp1 + temp2; \
218}
219
220 for( i = 0; i < 16; i++ )
221 {
222 GET_UINT64_BE( W[i], data, i << 3 );
223 }
224
225 for( ; i < 80; i++ )
226 {
227 W[i] = S1(W[i - 2]) + W[i - 7] +
228 S0(W[i - 15]) + W[i - 16];
229 }
230
231 A = ctx->state[0];
232 B = ctx->state[1];
233 C = ctx->state[2];
234 D = ctx->state[3];
235 E = ctx->state[4];
236 F = ctx->state[5];
237 G = ctx->state[6];
238 H = ctx->state[7];
239 i = 0;
240
241 do
242 {
243 P( A, B, C, D, E, F, G, H, W[i], K[i] ); i++;
244 P( H, A, B, C, D, E, F, G, W[i], K[i] ); i++;
245 P( G, H, A, B, C, D, E, F, W[i], K[i] ); i++;
246 P( F, G, H, A, B, C, D, E, W[i], K[i] ); i++;
247 P( E, F, G, H, A, B, C, D, W[i], K[i] ); i++;
248 P( D, E, F, G, H, A, B, C, W[i], K[i] ); i++;
249 P( C, D, E, F, G, H, A, B, W[i], K[i] ); i++;
250 P( B, C, D, E, F, G, H, A, W[i], K[i] ); i++;
251 }
252 while( i < 80 );
253
254 ctx->state[0] += A;
255 ctx->state[1] += B;
256 ctx->state[2] += C;
257 ctx->state[3] += D;
258 ctx->state[4] += E;
259 ctx->state[5] += F;
260 ctx->state[6] += G;
261 ctx->state[7] += H;
262}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200263#endif /* !MBEDTLS_SHA512_PROCESS_ALT */
Paul Bakker5121ce52009-01-03 21:22:43 +0000264
265/*
266 * SHA-512 process buffer
267 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200268void mbedtls_sha512_update( mbedtls_sha512_context *ctx, const unsigned char *input,
Paul Bakkerb9e4e2c2014-05-01 14:18:25 +0200269 size_t ilen )
Paul Bakker5121ce52009-01-03 21:22:43 +0000270{
Paul Bakker23986e52011-04-24 08:57:21 +0000271 size_t fill;
Paul Bakkerb8213a12011-07-11 08:16:18 +0000272 unsigned int left;
Paul Bakker5121ce52009-01-03 21:22:43 +0000273
Brian White12895d12014-04-11 11:29:42 -0400274 if( ilen == 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000275 return;
276
Paul Bakkerb8213a12011-07-11 08:16:18 +0000277 left = (unsigned int) (ctx->total[0] & 0x7F);
Paul Bakker27fdf462011-06-09 13:55:13 +0000278 fill = 128 - left;
Paul Bakker5121ce52009-01-03 21:22:43 +0000279
Paul Bakker5c2364c2012-10-01 14:41:15 +0000280 ctx->total[0] += (uint64_t) ilen;
Paul Bakker5121ce52009-01-03 21:22:43 +0000281
Paul Bakker5c2364c2012-10-01 14:41:15 +0000282 if( ctx->total[0] < (uint64_t) ilen )
Paul Bakker5121ce52009-01-03 21:22:43 +0000283 ctx->total[1]++;
284
285 if( left && ilen >= fill )
286 {
Paul Bakker3c2122f2013-06-24 19:03:14 +0200287 memcpy( (void *) (ctx->buffer + left), input, fill );
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200288 mbedtls_sha512_process( ctx, ctx->buffer );
Paul Bakker5121ce52009-01-03 21:22:43 +0000289 input += fill;
290 ilen -= fill;
291 left = 0;
292 }
293
294 while( ilen >= 128 )
295 {
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200296 mbedtls_sha512_process( ctx, input );
Paul Bakker5121ce52009-01-03 21:22:43 +0000297 input += 128;
298 ilen -= 128;
299 }
300
301 if( ilen > 0 )
Paul Bakker3c2122f2013-06-24 19:03:14 +0200302 memcpy( (void *) (ctx->buffer + left), input, ilen );
Paul Bakker5121ce52009-01-03 21:22:43 +0000303}
304
Paul Bakker5121ce52009-01-03 21:22:43 +0000305/*
306 * SHA-512 final digest
307 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200308void mbedtls_sha512_finish( mbedtls_sha512_context *ctx, unsigned char output[64] )
Paul Bakker5121ce52009-01-03 21:22:43 +0000309{
Manuel Pégourié-Gonnard69675d02018-06-28 12:10:27 +0200310 unsigned used;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000311 uint64_t high, low;
Paul Bakker5121ce52009-01-03 21:22:43 +0000312
Manuel Pégourié-Gonnard69675d02018-06-28 12:10:27 +0200313 /*
314 * Add padding: 0x80 then 0x00 until 16 bytes remain for the length
315 */
316 used = ctx->total[0] & 0x7F;
317
318 ctx->buffer[used++] = 0x80;
319
320 if( used <= 112 )
321 {
322 /* Enough room for padding + length in current block */
323 memset( ctx->buffer + used, 0, 112 - used );
324 }
325 else
326 {
327 /* We'll need an extra block */
328 memset( ctx->buffer + used, 0, 128 - used );
329
330 mbedtls_sha512_process( ctx, ctx->buffer );
331
332 memset( ctx->buffer, 0, 112 );
333 }
334
335 /*
336 * Add message length
337 */
Paul Bakker5121ce52009-01-03 21:22:43 +0000338 high = ( ctx->total[0] >> 61 )
339 | ( ctx->total[1] << 3 );
340 low = ( ctx->total[0] << 3 );
341
Manuel Pégourié-Gonnard69675d02018-06-28 12:10:27 +0200342 PUT_UINT64_BE( high, ctx->buffer, 112 );
343 PUT_UINT64_BE( low, ctx->buffer, 120 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000344
Manuel Pégourié-Gonnard69675d02018-06-28 12:10:27 +0200345 mbedtls_sha512_process( ctx, ctx->buffer );
Paul Bakker5121ce52009-01-03 21:22:43 +0000346
Manuel Pégourié-Gonnard69675d02018-06-28 12:10:27 +0200347 /*
348 * Output final state
349 */
Paul Bakker5121ce52009-01-03 21:22:43 +0000350 PUT_UINT64_BE( ctx->state[0], output, 0 );
351 PUT_UINT64_BE( ctx->state[1], output, 8 );
352 PUT_UINT64_BE( ctx->state[2], output, 16 );
353 PUT_UINT64_BE( ctx->state[3], output, 24 );
354 PUT_UINT64_BE( ctx->state[4], output, 32 );
355 PUT_UINT64_BE( ctx->state[5], output, 40 );
356
357 if( ctx->is384 == 0 )
358 {
359 PUT_UINT64_BE( ctx->state[6], output, 48 );
360 PUT_UINT64_BE( ctx->state[7], output, 56 );
361 }
362}
363
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200364#endif /* !MBEDTLS_SHA512_ALT */
Paul Bakker90995b52013-06-24 19:20:35 +0200365
Paul Bakker5121ce52009-01-03 21:22:43 +0000366/*
367 * output = SHA-512( input buffer )
368 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200369void mbedtls_sha512( const unsigned char *input, size_t ilen,
Paul Bakker9e36f042013-06-30 14:34:05 +0200370 unsigned char output[64], int is384 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000371{
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200372 mbedtls_sha512_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +0000373
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200374 mbedtls_sha512_init( &ctx );
375 mbedtls_sha512_starts( &ctx, is384 );
376 mbedtls_sha512_update( &ctx, input, ilen );
377 mbedtls_sha512_finish( &ctx, output );
378 mbedtls_sha512_free( &ctx );
Paul Bakker5121ce52009-01-03 21:22:43 +0000379}
380
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200381#if defined(MBEDTLS_SELF_TEST)
Paul Bakker5121ce52009-01-03 21:22:43 +0000382
383/*
384 * FIPS-180-2 test vectors
385 */
Manuel Pégourié-Gonnard28122e42015-03-11 09:13:42 +0000386static const unsigned char sha512_test_buf[3][113] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000387{
388 { "abc" },
389 { "abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmn"
390 "hijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu" },
391 { "" }
392};
393
Paul Bakker9e36f042013-06-30 14:34:05 +0200394static const int sha512_test_buflen[3] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000395{
396 3, 112, 1000
397};
398
Paul Bakker9e36f042013-06-30 14:34:05 +0200399static const unsigned char sha512_test_sum[6][64] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000400{
401 /*
402 * SHA-384 test vectors
403 */
404 { 0xCB, 0x00, 0x75, 0x3F, 0x45, 0xA3, 0x5E, 0x8B,
405 0xB5, 0xA0, 0x3D, 0x69, 0x9A, 0xC6, 0x50, 0x07,
406 0x27, 0x2C, 0x32, 0xAB, 0x0E, 0xDE, 0xD1, 0x63,
407 0x1A, 0x8B, 0x60, 0x5A, 0x43, 0xFF, 0x5B, 0xED,
408 0x80, 0x86, 0x07, 0x2B, 0xA1, 0xE7, 0xCC, 0x23,
409 0x58, 0xBA, 0xEC, 0xA1, 0x34, 0xC8, 0x25, 0xA7 },
410 { 0x09, 0x33, 0x0C, 0x33, 0xF7, 0x11, 0x47, 0xE8,
411 0x3D, 0x19, 0x2F, 0xC7, 0x82, 0xCD, 0x1B, 0x47,
412 0x53, 0x11, 0x1B, 0x17, 0x3B, 0x3B, 0x05, 0xD2,
413 0x2F, 0xA0, 0x80, 0x86, 0xE3, 0xB0, 0xF7, 0x12,
414 0xFC, 0xC7, 0xC7, 0x1A, 0x55, 0x7E, 0x2D, 0xB9,
415 0x66, 0xC3, 0xE9, 0xFA, 0x91, 0x74, 0x60, 0x39 },
416 { 0x9D, 0x0E, 0x18, 0x09, 0x71, 0x64, 0x74, 0xCB,
417 0x08, 0x6E, 0x83, 0x4E, 0x31, 0x0A, 0x4A, 0x1C,
418 0xED, 0x14, 0x9E, 0x9C, 0x00, 0xF2, 0x48, 0x52,
419 0x79, 0x72, 0xCE, 0xC5, 0x70, 0x4C, 0x2A, 0x5B,
420 0x07, 0xB8, 0xB3, 0xDC, 0x38, 0xEC, 0xC4, 0xEB,
421 0xAE, 0x97, 0xDD, 0xD8, 0x7F, 0x3D, 0x89, 0x85 },
422
423 /*
424 * SHA-512 test vectors
425 */
426 { 0xDD, 0xAF, 0x35, 0xA1, 0x93, 0x61, 0x7A, 0xBA,
427 0xCC, 0x41, 0x73, 0x49, 0xAE, 0x20, 0x41, 0x31,
428 0x12, 0xE6, 0xFA, 0x4E, 0x89, 0xA9, 0x7E, 0xA2,
429 0x0A, 0x9E, 0xEE, 0xE6, 0x4B, 0x55, 0xD3, 0x9A,
430 0x21, 0x92, 0x99, 0x2A, 0x27, 0x4F, 0xC1, 0xA8,
431 0x36, 0xBA, 0x3C, 0x23, 0xA3, 0xFE, 0xEB, 0xBD,
432 0x45, 0x4D, 0x44, 0x23, 0x64, 0x3C, 0xE8, 0x0E,
433 0x2A, 0x9A, 0xC9, 0x4F, 0xA5, 0x4C, 0xA4, 0x9F },
434 { 0x8E, 0x95, 0x9B, 0x75, 0xDA, 0xE3, 0x13, 0xDA,
435 0x8C, 0xF4, 0xF7, 0x28, 0x14, 0xFC, 0x14, 0x3F,
436 0x8F, 0x77, 0x79, 0xC6, 0xEB, 0x9F, 0x7F, 0xA1,
437 0x72, 0x99, 0xAE, 0xAD, 0xB6, 0x88, 0x90, 0x18,
438 0x50, 0x1D, 0x28, 0x9E, 0x49, 0x00, 0xF7, 0xE4,
439 0x33, 0x1B, 0x99, 0xDE, 0xC4, 0xB5, 0x43, 0x3A,
440 0xC7, 0xD3, 0x29, 0xEE, 0xB6, 0xDD, 0x26, 0x54,
441 0x5E, 0x96, 0xE5, 0x5B, 0x87, 0x4B, 0xE9, 0x09 },
442 { 0xE7, 0x18, 0x48, 0x3D, 0x0C, 0xE7, 0x69, 0x64,
443 0x4E, 0x2E, 0x42, 0xC7, 0xBC, 0x15, 0xB4, 0x63,
444 0x8E, 0x1F, 0x98, 0xB1, 0x3B, 0x20, 0x44, 0x28,
445 0x56, 0x32, 0xA8, 0x03, 0xAF, 0xA9, 0x73, 0xEB,
446 0xDE, 0x0F, 0xF2, 0x44, 0x87, 0x7E, 0xA6, 0x0A,
447 0x4C, 0xB0, 0x43, 0x2C, 0xE5, 0x77, 0xC3, 0x1B,
448 0xEB, 0x00, 0x9C, 0x5C, 0x2C, 0x49, 0xAA, 0x2E,
449 0x4E, 0xAD, 0xB2, 0x17, 0xAD, 0x8C, 0xC0, 0x9B }
450};
451
452/*
Paul Bakker5121ce52009-01-03 21:22:43 +0000453 * Checkup routine
454 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200455int mbedtls_sha512_self_test( int verbose )
Paul Bakker5121ce52009-01-03 21:22:43 +0000456{
Paul Bakker5b4af392014-06-26 12:09:34 +0200457 int i, j, k, buflen, ret = 0;
Paul Bakker5121ce52009-01-03 21:22:43 +0000458 unsigned char buf[1024];
Paul Bakker9e36f042013-06-30 14:34:05 +0200459 unsigned char sha512sum[64];
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200460 mbedtls_sha512_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +0000461
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200462 mbedtls_sha512_init( &ctx );
Paul Bakker5b4af392014-06-26 12:09:34 +0200463
Paul Bakker5121ce52009-01-03 21:22:43 +0000464 for( i = 0; i < 6; i++ )
465 {
466 j = i % 3;
467 k = i < 3;
468
469 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200470 mbedtls_printf( " SHA-%d test #%d: ", 512 - k * 128, j + 1 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000471
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200472 mbedtls_sha512_starts( &ctx, k );
Paul Bakker5121ce52009-01-03 21:22:43 +0000473
474 if( j == 2 )
475 {
476 memset( buf, 'a', buflen = 1000 );
477
478 for( j = 0; j < 1000; j++ )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200479 mbedtls_sha512_update( &ctx, buf, buflen );
Paul Bakker5121ce52009-01-03 21:22:43 +0000480 }
481 else
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200482 mbedtls_sha512_update( &ctx, sha512_test_buf[j],
Paul Bakker9e36f042013-06-30 14:34:05 +0200483 sha512_test_buflen[j] );
Paul Bakker5121ce52009-01-03 21:22:43 +0000484
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200485 mbedtls_sha512_finish( &ctx, sha512sum );
Paul Bakker5121ce52009-01-03 21:22:43 +0000486
Paul Bakker9e36f042013-06-30 14:34:05 +0200487 if( memcmp( sha512sum, sha512_test_sum[i], 64 - k * 16 ) != 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000488 {
489 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200490 mbedtls_printf( "failed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000491
Paul Bakker5b4af392014-06-26 12:09:34 +0200492 ret = 1;
493 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +0000494 }
495
496 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200497 mbedtls_printf( "passed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000498 }
499
500 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200501 mbedtls_printf( "\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000502
Paul Bakker5b4af392014-06-26 12:09:34 +0200503exit:
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200504 mbedtls_sha512_free( &ctx );
Paul Bakker5b4af392014-06-26 12:09:34 +0200505
506 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +0000507}
508
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200509#endif /* MBEDTLS_SELF_TEST */
Paul Bakker5121ce52009-01-03 21:22:43 +0000510
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200511#endif /* MBEDTLS_SHA512_C */