blob: 4dcec89657689fcd317615101c4b7aebc18f7f0b [file] [log] [blame]
Paul Bakker5121ce52009-01-03 21:22:43 +00001/*
2 * FIPS-180-2 compliant SHA-256 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-256 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_SHA256_C)
Paul Bakker5121ce52009-01-03 21:22:43 +000034
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000035#include "mbedtls/sha256.h"
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -050036#include "mbedtls/platform_util.h"
Paul Bakker5121ce52009-01-03 21:22:43 +000037
Rich Evans00ab4702015-02-06 13:43:58 +000038#include <string.h>
39
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020040#if defined(MBEDTLS_SELF_TEST)
41#if defined(MBEDTLS_PLATFORM_C)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000042#include "mbedtls/platform.h"
Paul Bakker7dc4c442014-02-01 22:50:26 +010043#else
Rich Evans00ab4702015-02-06 13:43:58 +000044#include <stdio.h>
Russ Butlerbb83b422016-10-12 17:36:50 -050045#include <stdlib.h>
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020046#define mbedtls_printf printf
Russ Butlerbb83b422016-10-12 17:36:50 -050047#define mbedtls_calloc calloc
48#define mbedtls_free free
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020049#endif /* MBEDTLS_PLATFORM_C */
50#endif /* MBEDTLS_SELF_TEST */
Paul Bakker7dc4c442014-02-01 22:50:26 +010051
Hanno Becker2f6de422018-12-20 10:22:32 +000052#define SHA256_VALIDATE_RET(cond) \
53 MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_SHA256_BAD_INPUT_DATA )
54#define SHA256_VALIDATE(cond) MBEDTLS_INTERNAL_VALIDATE( cond )
55
Manuel Pégourié-Gonnard8b2641d2015-08-27 20:03:46 +020056#if !defined(MBEDTLS_SHA256_ALT)
57
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020058void mbedtls_sha256_init( mbedtls_sha256_context *ctx )
Paul Bakker5b4af392014-06-26 12:09:34 +020059{
Hanno Becker8d215e72018-12-18 17:53:21 +000060 SHA256_VALIDATE( ctx != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +000061
Manuel Pégourié-Gonnard99419332019-10-03 10:40:57 +020062 memset( ctx, 0, sizeof( mbedtls_sha256_context ) );
Paul Bakker5b4af392014-06-26 12:09:34 +020063}
64
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020065void mbedtls_sha256_free( mbedtls_sha256_context *ctx )
Paul Bakker5b4af392014-06-26 12:09:34 +020066{
67 if( ctx == NULL )
68 return;
69
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -050070 mbedtls_platform_zeroize( ctx, sizeof( mbedtls_sha256_context ) );
Paul Bakker5b4af392014-06-26 12:09:34 +020071}
72
Manuel Pégourié-Gonnard16d412f2015-07-06 15:26:26 +020073void mbedtls_sha256_clone( mbedtls_sha256_context *dst,
74 const mbedtls_sha256_context *src )
75{
Hanno Becker8d215e72018-12-18 17:53:21 +000076 SHA256_VALIDATE( dst != NULL );
77 SHA256_VALIDATE( src != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +000078
Manuel Pégourié-Gonnard16d412f2015-07-06 15:26:26 +020079 *dst = *src;
80}
81
Paul Bakker5121ce52009-01-03 21:22:43 +000082/*
83 * SHA-256 context setup
84 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +010085int mbedtls_sha256_starts_ret( mbedtls_sha256_context *ctx, int is224 )
Paul Bakker5121ce52009-01-03 21:22:43 +000086{
Hanno Becker8d215e72018-12-18 17:53:21 +000087 SHA256_VALIDATE_RET( ctx != NULL );
Manuel Pégourié-Gonnardefd34482019-09-02 14:41:19 +020088#if defined(MBEDTLS_SHA256_NO_SHA224)
89 SHA256_VALIDATE_RET( is224 == 0 );
90 (void) is224;
91#else
Hanno Becker8d215e72018-12-18 17:53:21 +000092 SHA256_VALIDATE_RET( is224 == 0 || is224 == 1 );
Manuel Pégourié-Gonnardefd34482019-09-02 14:41:19 +020093#endif
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +000094
Paul Bakker5121ce52009-01-03 21:22:43 +000095 ctx->total[0] = 0;
96 ctx->total[1] = 0;
97
Manuel Pégourié-Gonnardefd34482019-09-02 14:41:19 +020098#if !defined(MBEDTLS_SHA256_NO_SHA224)
99 ctx->is224 = is224;
100
101 if( is224 == 1 )
102 {
103 /* SHA-224 */
104 ctx->state[0] = 0xC1059ED8;
105 ctx->state[1] = 0x367CD507;
106 ctx->state[2] = 0x3070DD17;
107 ctx->state[3] = 0xF70E5939;
108 ctx->state[4] = 0xFFC00B31;
109 ctx->state[5] = 0x68581511;
110 ctx->state[6] = 0x64F98FA7;
111 ctx->state[7] = 0xBEFA4FA4;
112 }
113 else
114#endif
Paul Bakker5121ce52009-01-03 21:22:43 +0000115 {
116 /* SHA-256 */
117 ctx->state[0] = 0x6A09E667;
118 ctx->state[1] = 0xBB67AE85;
119 ctx->state[2] = 0x3C6EF372;
120 ctx->state[3] = 0xA54FF53A;
121 ctx->state[4] = 0x510E527F;
122 ctx->state[5] = 0x9B05688C;
123 ctx->state[6] = 0x1F83D9AB;
124 ctx->state[7] = 0x5BE0CD19;
125 }
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100126
127 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000128}
129
Jaeden Amero041039f2018-02-19 15:28:08 +0000130#if !defined(MBEDTLS_DEPRECATED_REMOVED)
131void mbedtls_sha256_starts( mbedtls_sha256_context *ctx,
132 int is224 )
133{
134 mbedtls_sha256_starts_ret( ctx, is224 );
135}
136#endif
137
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200138#if !defined(MBEDTLS_SHA256_PROCESS_ALT)
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200139static const uint32_t K[] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000140{
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200141 0x428A2F98, 0x71374491, 0xB5C0FBCF, 0xE9B5DBA5,
142 0x3956C25B, 0x59F111F1, 0x923F82A4, 0xAB1C5ED5,
143 0xD807AA98, 0x12835B01, 0x243185BE, 0x550C7DC3,
144 0x72BE5D74, 0x80DEB1FE, 0x9BDC06A7, 0xC19BF174,
145 0xE49B69C1, 0xEFBE4786, 0x0FC19DC6, 0x240CA1CC,
146 0x2DE92C6F, 0x4A7484AA, 0x5CB0A9DC, 0x76F988DA,
147 0x983E5152, 0xA831C66D, 0xB00327C8, 0xBF597FC7,
148 0xC6E00BF3, 0xD5A79147, 0x06CA6351, 0x14292967,
149 0x27B70A85, 0x2E1B2138, 0x4D2C6DFC, 0x53380D13,
150 0x650A7354, 0x766A0ABB, 0x81C2C92E, 0x92722C85,
151 0xA2BFE8A1, 0xA81A664B, 0xC24B8B70, 0xC76C51A3,
152 0xD192E819, 0xD6990624, 0xF40E3585, 0x106AA070,
153 0x19A4C116, 0x1E376C08, 0x2748774C, 0x34B0BCB5,
154 0x391C0CB3, 0x4ED8AA4A, 0x5B9CCA4F, 0x682E6FF3,
155 0x748F82EE, 0x78A5636F, 0x84C87814, 0x8CC70208,
156 0x90BEFFFA, 0xA4506CEB, 0xBEF9A3F7, 0xC67178F2,
157};
Paul Bakker5121ce52009-01-03 21:22:43 +0000158
Hanno Beckerd6028a12018-10-15 12:01:35 +0100159#define SHR(x,n) (((x) & 0xFFFFFFFF) >> (n))
160#define ROTR(x,n) (SHR(x,n) | ((x) << (32 - (n))))
Paul Bakker5121ce52009-01-03 21:22:43 +0000161
162#define S0(x) (ROTR(x, 7) ^ ROTR(x,18) ^ SHR(x, 3))
163#define S1(x) (ROTR(x,17) ^ ROTR(x,19) ^ SHR(x,10))
164
165#define S2(x) (ROTR(x, 2) ^ ROTR(x,13) ^ ROTR(x,22))
166#define S3(x) (ROTR(x, 6) ^ ROTR(x,11) ^ ROTR(x,25))
167
Hanno Beckerd6028a12018-10-15 12:01:35 +0100168#define F0(x,y,z) (((x) & (y)) | ((z) & ((x) | (y))))
169#define F1(x,y,z) ((z) ^ ((x) & ((y) ^ (z))))
Paul Bakker5121ce52009-01-03 21:22:43 +0000170
171#define R(t) \
Hanno Beckerd6028a12018-10-15 12:01:35 +0100172 ( \
173 W[t] = S1(W[(t) - 2]) + W[(t) - 7] + \
174 S0(W[(t) - 15]) + W[(t) - 16] \
175 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000176
Hanno Beckerd6028a12018-10-15 12:01:35 +0100177#define P(a,b,c,d,e,f,g,h,x,K) \
178 do \
179 { \
Hanno Becker3ac21ac2018-10-26 09:13:26 +0100180 temp1 = (h) + S3(e) + F1((e),(f),(g)) + (K) + (x); \
181 temp2 = S2(a) + F0((a),(b),(c)); \
Hanno Beckerd6028a12018-10-15 12:01:35 +0100182 (d) += temp1; (h) = temp1 + temp2; \
183 } while( 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000184
Andres Amaya Garciacccfe082017-06-28 10:36:39 +0100185int mbedtls_internal_sha256_process( mbedtls_sha256_context *ctx,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100186 const unsigned char data[64] )
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200187{
188 uint32_t temp1, temp2, W[64];
189 uint32_t A[8];
190 unsigned int i;
Paul Bakker5121ce52009-01-03 21:22:43 +0000191
Hanno Becker8d215e72018-12-18 17:53:21 +0000192 SHA256_VALIDATE_RET( ctx != NULL );
193 SHA256_VALIDATE_RET( (const unsigned char *)data != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +0000194
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200195 for( i = 0; i < 8; i++ )
196 A[i] = ctx->state[i];
197
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200198#if defined(MBEDTLS_SHA256_SMALLER)
Jarno Lamsabb86c522020-01-07 13:33:45 +0200199 {
200 uint32_t offset = mbedtls_platform_random_in_range(16);
201 mbedtls_platform_memset( W, 0, sizeof( W ) );
202
203 for( i = offset; i < 16; i++ )
204 {
205 W[i] = (uint32_t)mbedtls_platform_get_uint32_be( &data[4 * i] );
206 }
207 for( i = 0; i < offset; i++ )
208 {
209 W[i] = (uint32_t)mbedtls_platform_get_uint32_be( &data[4 * i] );
210 }
211 }
212
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200213 for( i = 0; i < 64; i++ )
214 {
Jarno Lamsabb86c522020-01-07 13:33:45 +0200215 if( i >= 16 )
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200216 R( i );
217
218 P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i], K[i] );
219
220 temp1 = A[7]; A[7] = A[6]; A[6] = A[5]; A[5] = A[4]; A[4] = A[3];
221 A[3] = A[2]; A[2] = A[1]; A[1] = A[0]; A[0] = temp1;
222 }
223#else /* MBEDTLS_SHA256_SMALLER */
224 for( i = 0; i < 16; i++ )
Arto Kinnunen4f4849a2019-09-09 10:21:18 +0300225 W[i] = (uint32_t)mbedtls_platform_get_uint32_be( &data[4 * i] );
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200226
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200227 for( i = 0; i < 16; i += 8 )
228 {
229 P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i+0], K[i+0] );
230 P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], W[i+1], K[i+1] );
231 P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], W[i+2], K[i+2] );
232 P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], W[i+3], K[i+3] );
233 P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], W[i+4], K[i+4] );
234 P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], W[i+5], K[i+5] );
235 P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], W[i+6], K[i+6] );
236 P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], W[i+7], K[i+7] );
237 }
238
239 for( i = 16; i < 64; i += 8 )
240 {
241 P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], R(i+0), K[i+0] );
242 P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], R(i+1), K[i+1] );
243 P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], R(i+2), K[i+2] );
244 P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], R(i+3), K[i+3] );
245 P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], R(i+4), K[i+4] );
246 P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], R(i+5), K[i+5] );
247 P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], R(i+6), K[i+6] );
248 P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], R(i+7), K[i+7] );
249 }
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200250#endif /* MBEDTLS_SHA256_SMALLER */
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200251
252 for( i = 0; i < 8; i++ )
253 ctx->state[i] += A[i];
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100254
255 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000256}
Jaeden Amero041039f2018-02-19 15:28:08 +0000257
258#if !defined(MBEDTLS_DEPRECATED_REMOVED)
259void mbedtls_sha256_process( mbedtls_sha256_context *ctx,
260 const unsigned char data[64] )
261{
262 mbedtls_internal_sha256_process( ctx, data );
263}
264#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200265#endif /* !MBEDTLS_SHA256_PROCESS_ALT */
Paul Bakker5121ce52009-01-03 21:22:43 +0000266
267/*
268 * SHA-256 process buffer
269 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100270int mbedtls_sha256_update_ret( mbedtls_sha256_context *ctx,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100271 const unsigned char *input,
272 size_t ilen )
Paul Bakker5121ce52009-01-03 21:22:43 +0000273{
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100274 int ret;
Paul Bakker23986e52011-04-24 08:57:21 +0000275 size_t fill;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000276 uint32_t left;
Paul Bakker5121ce52009-01-03 21:22:43 +0000277
Hanno Becker8d215e72018-12-18 17:53:21 +0000278 SHA256_VALIDATE_RET( ctx != NULL );
279 SHA256_VALIDATE_RET( ilen == 0 || input != NULL );
Hanno Becker596e0142018-12-18 15:00:38 +0000280
Brian White12895d12014-04-11 11:29:42 -0400281 if( ilen == 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100282 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000283
284 left = ctx->total[0] & 0x3F;
285 fill = 64 - left;
286
Paul Bakker5c2364c2012-10-01 14:41:15 +0000287 ctx->total[0] += (uint32_t) ilen;
Paul Bakker5121ce52009-01-03 21:22:43 +0000288 ctx->total[0] &= 0xFFFFFFFF;
289
Paul Bakker5c2364c2012-10-01 14:41:15 +0000290 if( ctx->total[0] < (uint32_t) ilen )
Paul Bakker5121ce52009-01-03 21:22:43 +0000291 ctx->total[1]++;
292
293 if( left && ilen >= fill )
294 {
Teppo Järvelin91d79382019-10-02 09:09:31 +0300295 mbedtls_platform_memcpy( (void *) (ctx->buffer + left), input, fill );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100296
Andres Amaya Garciacccfe082017-06-28 10:36:39 +0100297 if( ( ret = mbedtls_internal_sha256_process( ctx, ctx->buffer ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100298 return( ret );
299
Paul Bakker5121ce52009-01-03 21:22:43 +0000300 input += fill;
301 ilen -= fill;
302 left = 0;
303 }
304
305 while( ilen >= 64 )
306 {
Andres Amaya Garciacccfe082017-06-28 10:36:39 +0100307 if( ( ret = mbedtls_internal_sha256_process( ctx, input ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100308 return( ret );
309
Paul Bakker5121ce52009-01-03 21:22:43 +0000310 input += 64;
311 ilen -= 64;
312 }
313
314 if( ilen > 0 )
Teppo Järvelin91d79382019-10-02 09:09:31 +0300315 mbedtls_platform_memcpy( (void *) (ctx->buffer + left), input, ilen );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100316
317 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000318}
319
Jaeden Amero041039f2018-02-19 15:28:08 +0000320#if !defined(MBEDTLS_DEPRECATED_REMOVED)
321void mbedtls_sha256_update( mbedtls_sha256_context *ctx,
322 const unsigned char *input,
323 size_t ilen )
324{
325 mbedtls_sha256_update_ret( ctx, input, ilen );
326}
327#endif
328
Paul Bakker5121ce52009-01-03 21:22:43 +0000329/*
330 * SHA-256 final digest
331 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100332int mbedtls_sha256_finish_ret( mbedtls_sha256_context *ctx,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100333 unsigned char output[32] )
Paul Bakker5121ce52009-01-03 21:22:43 +0000334{
Arto Kinnunen9b3b1942019-09-09 17:02:35 +0300335 int ret, s_pos, o_pos;
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200336 uint32_t used;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000337 uint32_t high, low;
Jarno Lamsabb86c522020-01-07 13:33:45 +0200338 uint32_t offset = 0;
Paul Bakker5121ce52009-01-03 21:22:43 +0000339
Hanno Becker8d215e72018-12-18 17:53:21 +0000340 SHA256_VALIDATE_RET( ctx != NULL );
341 SHA256_VALIDATE_RET( (unsigned char *)output != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +0000342
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200343 /*
344 * Add padding: 0x80 then 0x00 until 8 bytes remain for the length
345 */
346 used = ctx->total[0] & 0x3F;
347
348 ctx->buffer[used++] = 0x80;
349
350 if( used <= 56 )
351 {
352 /* Enough room for padding + length in current block */
Manuel Pégourié-Gonnard7a346b82019-10-02 14:47:01 +0200353 mbedtls_platform_memset( ctx->buffer + used, 0, 56 - used );
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200354 }
355 else
356 {
357 /* We'll need an extra block */
Manuel Pégourié-Gonnard7a346b82019-10-02 14:47:01 +0200358 mbedtls_platform_memset( ctx->buffer + used, 0, 64 - used );
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200359
360 if( ( ret = mbedtls_internal_sha256_process( ctx, ctx->buffer ) ) != 0 )
361 return( ret );
362
Manuel Pégourié-Gonnard7a346b82019-10-02 14:47:01 +0200363 mbedtls_platform_memset( ctx->buffer, 0, 56 );
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200364 }
365
366 /*
367 * Add message length
368 */
Paul Bakker5121ce52009-01-03 21:22:43 +0000369 high = ( ctx->total[0] >> 29 )
370 | ( ctx->total[1] << 3 );
371 low = ( ctx->total[0] << 3 );
372
Arto Kinnunen3d7439e2019-09-10 11:30:40 +0300373 (void)mbedtls_platform_put_uint32_be( ctx->buffer + 56, high );
374 (void)mbedtls_platform_put_uint32_be( ctx->buffer + 60, low );
Paul Bakker5121ce52009-01-03 21:22:43 +0000375
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200376 if( ( ret = mbedtls_internal_sha256_process( ctx, ctx->buffer ) ) != 0 )
Andres Amaya Garciaaa464ef2017-07-21 14:21:53 +0100377 return( ret );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100378
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200379 /*
380 * Output final state
381 */
Jarno Lamsabb86c522020-01-07 13:33:45 +0200382 offset = mbedtls_platform_random_in_range(7);
Arto Kinnunen0b62ce82019-09-04 14:04:57 +0300383
Jarno Lamsabb86c522020-01-07 13:33:45 +0200384 mbedtls_platform_memset( output, 0, 32 );
385
386 for( s_pos = offset, o_pos = offset * 4; s_pos < 7;
387 s_pos++, o_pos += 4 )
Arto Kinnunen0b62ce82019-09-04 14:04:57 +0300388 {
Arto Kinnunen3d7439e2019-09-10 11:30:40 +0300389 (void)mbedtls_platform_put_uint32_be( &output[o_pos],
Jarno Lamsabb86c522020-01-07 13:33:45 +0200390 ctx->state[s_pos] );
Arto Kinnunen0b62ce82019-09-04 14:04:57 +0300391 }
Paul Bakker5121ce52009-01-03 21:22:43 +0000392
Manuel Pégourié-Gonnard8463d292019-07-16 14:39:55 +0200393#if !defined(MBEDTLS_SHA256_NO_SHA224)
Paul Bakker5121ce52009-01-03 21:22:43 +0000394 if( ctx->is224 == 0 )
Manuel Pégourié-Gonnard8463d292019-07-16 14:39:55 +0200395#endif
Arto Kinnunen3d7439e2019-09-10 11:30:40 +0300396 (void)mbedtls_platform_put_uint32_be( &output[28], ctx->state[7] );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100397
Jarno Lamsabb86c522020-01-07 13:33:45 +0200398 for( s_pos = 0, o_pos = 0; s_pos < (int)offset; s_pos++, o_pos += 4 )
399 {
400 (void)mbedtls_platform_put_uint32_be( &output[o_pos],
401 ctx->state[s_pos] );
402 }
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100403 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000404}
405
Jaeden Amero041039f2018-02-19 15:28:08 +0000406#if !defined(MBEDTLS_DEPRECATED_REMOVED)
407void mbedtls_sha256_finish( mbedtls_sha256_context *ctx,
408 unsigned char output[32] )
409{
410 mbedtls_sha256_finish_ret( ctx, output );
411}
412#endif
413
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200414#endif /* !MBEDTLS_SHA256_ALT */
Paul Bakker90995b52013-06-24 19:20:35 +0200415
Paul Bakker5121ce52009-01-03 21:22:43 +0000416/*
417 * output = SHA-256( input buffer )
418 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100419int mbedtls_sha256_ret( const unsigned char *input,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100420 size_t ilen,
421 unsigned char output[32],
422 int is224 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000423{
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100424 int ret;
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200425 mbedtls_sha256_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +0000426
Hanno Becker8d215e72018-12-18 17:53:21 +0000427 SHA256_VALIDATE_RET( is224 == 0 || is224 == 1 );
428 SHA256_VALIDATE_RET( ilen == 0 || input != NULL );
429 SHA256_VALIDATE_RET( (unsigned char *)output != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +0000430
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200431 mbedtls_sha256_init( &ctx );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100432
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100433 if( ( ret = mbedtls_sha256_starts_ret( &ctx, is224 ) ) != 0 )
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100434 goto exit;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100435
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100436 if( ( ret = mbedtls_sha256_update_ret( &ctx, input, ilen ) ) != 0 )
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100437 goto exit;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100438
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100439 if( ( ret = mbedtls_sha256_finish_ret( &ctx, output ) ) != 0 )
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100440 goto exit;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100441
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100442exit:
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200443 mbedtls_sha256_free( &ctx );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100444
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100445 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +0000446}
447
Jaeden Amero041039f2018-02-19 15:28:08 +0000448#if !defined(MBEDTLS_DEPRECATED_REMOVED)
449void mbedtls_sha256( const unsigned char *input,
450 size_t ilen,
451 unsigned char output[32],
452 int is224 )
453{
454 mbedtls_sha256_ret( input, ilen, output, is224 );
455}
456#endif
457
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200458#if defined(MBEDTLS_SELF_TEST)
Paul Bakker5121ce52009-01-03 21:22:43 +0000459/*
460 * FIPS-180-2 test vectors
461 */
Manuel Pégourié-Gonnard28122e42015-03-11 09:13:42 +0000462static const unsigned char sha256_test_buf[3][57] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000463{
464 { "abc" },
465 { "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" },
466 { "" }
467};
468
Andres Amaya Garcia2d0aa8b2017-07-21 14:57:26 +0100469static const size_t sha256_test_buflen[3] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000470{
471 3, 56, 1000
472};
473
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200474static const unsigned char sha256_test_sum[][32] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000475{
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200476#if !defined(MBEDTLS_SHA256_NO_SHA224)
Paul Bakker5121ce52009-01-03 21:22:43 +0000477 /*
478 * SHA-224 test vectors
479 */
480 { 0x23, 0x09, 0x7D, 0x22, 0x34, 0x05, 0xD8, 0x22,
481 0x86, 0x42, 0xA4, 0x77, 0xBD, 0xA2, 0x55, 0xB3,
482 0x2A, 0xAD, 0xBC, 0xE4, 0xBD, 0xA0, 0xB3, 0xF7,
483 0xE3, 0x6C, 0x9D, 0xA7 },
484 { 0x75, 0x38, 0x8B, 0x16, 0x51, 0x27, 0x76, 0xCC,
485 0x5D, 0xBA, 0x5D, 0xA1, 0xFD, 0x89, 0x01, 0x50,
486 0xB0, 0xC6, 0x45, 0x5C, 0xB4, 0xF5, 0x8B, 0x19,
487 0x52, 0x52, 0x25, 0x25 },
488 { 0x20, 0x79, 0x46, 0x55, 0x98, 0x0C, 0x91, 0xD8,
489 0xBB, 0xB4, 0xC1, 0xEA, 0x97, 0x61, 0x8A, 0x4B,
490 0xF0, 0x3F, 0x42, 0x58, 0x19, 0x48, 0xB2, 0xEE,
491 0x4E, 0xE7, 0xAD, 0x67 },
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200492#endif /* !MBEDTLS_SHA256_NO_SHA224 */
Paul Bakker5121ce52009-01-03 21:22:43 +0000493
494 /*
495 * SHA-256 test vectors
496 */
497 { 0xBA, 0x78, 0x16, 0xBF, 0x8F, 0x01, 0xCF, 0xEA,
498 0x41, 0x41, 0x40, 0xDE, 0x5D, 0xAE, 0x22, 0x23,
499 0xB0, 0x03, 0x61, 0xA3, 0x96, 0x17, 0x7A, 0x9C,
500 0xB4, 0x10, 0xFF, 0x61, 0xF2, 0x00, 0x15, 0xAD },
501 { 0x24, 0x8D, 0x6A, 0x61, 0xD2, 0x06, 0x38, 0xB8,
502 0xE5, 0xC0, 0x26, 0x93, 0x0C, 0x3E, 0x60, 0x39,
503 0xA3, 0x3C, 0xE4, 0x59, 0x64, 0xFF, 0x21, 0x67,
504 0xF6, 0xEC, 0xED, 0xD4, 0x19, 0xDB, 0x06, 0xC1 },
505 { 0xCD, 0xC7, 0x6E, 0x5C, 0x99, 0x14, 0xFB, 0x92,
506 0x81, 0xA1, 0xC7, 0xE2, 0x84, 0xD7, 0x3E, 0x67,
507 0xF1, 0x80, 0x9A, 0x48, 0xA4, 0x97, 0x20, 0x0E,
508 0x04, 0x6D, 0x39, 0xCC, 0xC7, 0x11, 0x2C, 0xD0 }
509};
510
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200511#define SHA256_TEST_SUM_N \
512 ( sizeof( sha256_test_sum ) / sizeof( sha256_test_sum[0] ) )
513
Paul Bakker5121ce52009-01-03 21:22:43 +0000514/*
Paul Bakker5121ce52009-01-03 21:22:43 +0000515 * Checkup routine
516 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200517int mbedtls_sha256_self_test( int verbose )
Paul Bakker5121ce52009-01-03 21:22:43 +0000518{
Paul Bakker5b4af392014-06-26 12:09:34 +0200519 int i, j, k, buflen, ret = 0;
Russ Butlerbb83b422016-10-12 17:36:50 -0500520 unsigned char *buf;
Paul Bakker9e36f042013-06-30 14:34:05 +0200521 unsigned char sha256sum[32];
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200522 mbedtls_sha256_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +0000523
Russ Butlerbb83b422016-10-12 17:36:50 -0500524 buf = mbedtls_calloc( 1024, sizeof(unsigned char) );
525 if( NULL == buf )
526 {
527 if( verbose != 0 )
528 mbedtls_printf( "Buffer allocation failed\n" );
529
530 return( 1 );
531 }
532
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200533 mbedtls_sha256_init( &ctx );
Paul Bakker5b4af392014-06-26 12:09:34 +0200534
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200535 for( i = 0; i < (int) SHA256_TEST_SUM_N; i++ )
Paul Bakker5121ce52009-01-03 21:22:43 +0000536 {
537 j = i % 3;
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200538#if !defined(MBEDTLS_SHA256_NO_SHA224)
Paul Bakker5121ce52009-01-03 21:22:43 +0000539 k = i < 3;
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200540#else
541 k = 0;
542#endif
Paul Bakker5121ce52009-01-03 21:22:43 +0000543
544 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200545 mbedtls_printf( " SHA-%d test #%d: ", 256 - k * 32, j + 1 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000546
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100547 if( ( ret = mbedtls_sha256_starts_ret( &ctx, k ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100548 goto fail;
Paul Bakker5121ce52009-01-03 21:22:43 +0000549
550 if( j == 2 )
551 {
Teppo Järvelind49d2b62019-10-30 13:48:12 +0200552 memset( buf, 'a', buflen = 1000 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000553
554 for( j = 0; j < 1000; j++ )
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100555 {
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100556 ret = mbedtls_sha256_update_ret( &ctx, buf, buflen );
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100557 if( ret != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100558 goto fail;
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100559 }
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100560
Paul Bakker5121ce52009-01-03 21:22:43 +0000561 }
562 else
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100563 {
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100564 ret = mbedtls_sha256_update_ret( &ctx, sha256_test_buf[j],
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100565 sha256_test_buflen[j] );
566 if( ret != 0 )
567 goto fail;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100568 }
Paul Bakker5121ce52009-01-03 21:22:43 +0000569
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100570 if( ( ret = mbedtls_sha256_finish_ret( &ctx, sha256sum ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100571 goto fail;
572
Paul Bakker5121ce52009-01-03 21:22:43 +0000573
Paul Bakker9e36f042013-06-30 14:34:05 +0200574 if( memcmp( sha256sum, sha256_test_sum[i], 32 - k * 4 ) != 0 )
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100575 {
576 ret = 1;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100577 goto fail;
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100578 }
Paul Bakker5121ce52009-01-03 21:22:43 +0000579
580 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200581 mbedtls_printf( "passed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000582 }
583
584 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200585 mbedtls_printf( "\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000586
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100587 goto exit;
588
589fail:
590 if( verbose != 0 )
591 mbedtls_printf( "failed\n" );
592
Paul Bakker5b4af392014-06-26 12:09:34 +0200593exit:
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200594 mbedtls_sha256_free( &ctx );
Russ Butlerbb83b422016-10-12 17:36:50 -0500595 mbedtls_free( buf );
Paul Bakker5b4af392014-06-26 12:09:34 +0200596
597 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +0000598}
599
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200600#endif /* MBEDTLS_SELF_TEST */
Paul Bakker5121ce52009-01-03 21:22:43 +0000601
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200602#endif /* MBEDTLS_SHA256_C */