blob: 493e88ed5153dd34c625fd6155c8714e03b89047 [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"
Andrzej Kurek78f77eb2020-06-04 08:09:53 -040037#include "mbedtls/platform.h"
Paul Bakker5121ce52009-01-03 21:22:43 +000038
Rich Evans00ab4702015-02-06 13:43:58 +000039#include <string.h>
40
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020041#if defined(MBEDTLS_SELF_TEST)
42#if defined(MBEDTLS_PLATFORM_C)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000043#include "mbedtls/platform.h"
Paul Bakker7dc4c442014-02-01 22:50:26 +010044#else
Rich Evans00ab4702015-02-06 13:43:58 +000045#include <stdio.h>
Russ Butlerbb83b422016-10-12 17:36:50 -050046#include <stdlib.h>
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020047#define mbedtls_printf printf
Russ Butlerbb83b422016-10-12 17:36:50 -050048#define mbedtls_calloc calloc
49#define mbedtls_free free
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020050#endif /* MBEDTLS_PLATFORM_C */
51#endif /* MBEDTLS_SELF_TEST */
Paul Bakker7dc4c442014-02-01 22:50:26 +010052
Hanno Becker2f6de422018-12-20 10:22:32 +000053#define SHA256_VALIDATE_RET(cond) \
54 MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_SHA256_BAD_INPUT_DATA )
55#define SHA256_VALIDATE(cond) MBEDTLS_INTERNAL_VALIDATE( cond )
56
Manuel Pégourié-Gonnard8b2641d2015-08-27 20:03:46 +020057#if !defined(MBEDTLS_SHA256_ALT)
58
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020059void mbedtls_sha256_init( mbedtls_sha256_context *ctx )
Paul Bakker5b4af392014-06-26 12:09:34 +020060{
Hanno Becker8d215e72018-12-18 17:53:21 +000061 SHA256_VALIDATE( ctx != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +000062
Manuel Pégourié-Gonnard99419332019-10-03 10:40:57 +020063 memset( ctx, 0, sizeof( mbedtls_sha256_context ) );
Paul Bakker5b4af392014-06-26 12:09:34 +020064}
65
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020066void mbedtls_sha256_free( mbedtls_sha256_context *ctx )
Paul Bakker5b4af392014-06-26 12:09:34 +020067{
68 if( ctx == NULL )
69 return;
70
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -050071 mbedtls_platform_zeroize( ctx, sizeof( mbedtls_sha256_context ) );
Paul Bakker5b4af392014-06-26 12:09:34 +020072}
73
Manuel Pégourié-Gonnard16d412f2015-07-06 15:26:26 +020074void mbedtls_sha256_clone( mbedtls_sha256_context *dst,
75 const mbedtls_sha256_context *src )
76{
Hanno Becker8d215e72018-12-18 17:53:21 +000077 SHA256_VALIDATE( dst != NULL );
78 SHA256_VALIDATE( src != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +000079
Manuel Pégourié-Gonnard16d412f2015-07-06 15:26:26 +020080 *dst = *src;
81}
82
Paul Bakker5121ce52009-01-03 21:22:43 +000083/*
84 * SHA-256 context setup
85 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +010086int mbedtls_sha256_starts_ret( mbedtls_sha256_context *ctx, int is224 )
Paul Bakker5121ce52009-01-03 21:22:43 +000087{
Hanno Becker8d215e72018-12-18 17:53:21 +000088 SHA256_VALIDATE_RET( ctx != NULL );
Manuel Pégourié-Gonnardefd34482019-09-02 14:41:19 +020089#if defined(MBEDTLS_SHA256_NO_SHA224)
90 SHA256_VALIDATE_RET( is224 == 0 );
91 (void) is224;
92#else
Hanno Becker8d215e72018-12-18 17:53:21 +000093 SHA256_VALIDATE_RET( is224 == 0 || is224 == 1 );
Manuel Pégourié-Gonnardefd34482019-09-02 14:41:19 +020094#endif
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +000095
Paul Bakker5121ce52009-01-03 21:22:43 +000096 ctx->total[0] = 0;
97 ctx->total[1] = 0;
98
Manuel Pégourié-Gonnardefd34482019-09-02 14:41:19 +020099#if !defined(MBEDTLS_SHA256_NO_SHA224)
100 ctx->is224 = is224;
101
102 if( is224 == 1 )
103 {
104 /* SHA-224 */
105 ctx->state[0] = 0xC1059ED8;
106 ctx->state[1] = 0x367CD507;
107 ctx->state[2] = 0x3070DD17;
108 ctx->state[3] = 0xF70E5939;
109 ctx->state[4] = 0xFFC00B31;
110 ctx->state[5] = 0x68581511;
111 ctx->state[6] = 0x64F98FA7;
112 ctx->state[7] = 0xBEFA4FA4;
113 }
114 else
115#endif
Paul Bakker5121ce52009-01-03 21:22:43 +0000116 {
117 /* SHA-256 */
118 ctx->state[0] = 0x6A09E667;
119 ctx->state[1] = 0xBB67AE85;
120 ctx->state[2] = 0x3C6EF372;
121 ctx->state[3] = 0xA54FF53A;
122 ctx->state[4] = 0x510E527F;
123 ctx->state[5] = 0x9B05688C;
124 ctx->state[6] = 0x1F83D9AB;
125 ctx->state[7] = 0x5BE0CD19;
126 }
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100127
128 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000129}
130
Jaeden Amero041039f2018-02-19 15:28:08 +0000131#if !defined(MBEDTLS_DEPRECATED_REMOVED)
132void mbedtls_sha256_starts( mbedtls_sha256_context *ctx,
133 int is224 )
134{
135 mbedtls_sha256_starts_ret( ctx, is224 );
136}
137#endif
138
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200139#if !defined(MBEDTLS_SHA256_PROCESS_ALT)
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200140static const uint32_t K[] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000141{
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200142 0x428A2F98, 0x71374491, 0xB5C0FBCF, 0xE9B5DBA5,
143 0x3956C25B, 0x59F111F1, 0x923F82A4, 0xAB1C5ED5,
144 0xD807AA98, 0x12835B01, 0x243185BE, 0x550C7DC3,
145 0x72BE5D74, 0x80DEB1FE, 0x9BDC06A7, 0xC19BF174,
146 0xE49B69C1, 0xEFBE4786, 0x0FC19DC6, 0x240CA1CC,
147 0x2DE92C6F, 0x4A7484AA, 0x5CB0A9DC, 0x76F988DA,
148 0x983E5152, 0xA831C66D, 0xB00327C8, 0xBF597FC7,
149 0xC6E00BF3, 0xD5A79147, 0x06CA6351, 0x14292967,
150 0x27B70A85, 0x2E1B2138, 0x4D2C6DFC, 0x53380D13,
151 0x650A7354, 0x766A0ABB, 0x81C2C92E, 0x92722C85,
152 0xA2BFE8A1, 0xA81A664B, 0xC24B8B70, 0xC76C51A3,
153 0xD192E819, 0xD6990624, 0xF40E3585, 0x106AA070,
154 0x19A4C116, 0x1E376C08, 0x2748774C, 0x34B0BCB5,
155 0x391C0CB3, 0x4ED8AA4A, 0x5B9CCA4F, 0x682E6FF3,
156 0x748F82EE, 0x78A5636F, 0x84C87814, 0x8CC70208,
157 0x90BEFFFA, 0xA4506CEB, 0xBEF9A3F7, 0xC67178F2,
158};
Paul Bakker5121ce52009-01-03 21:22:43 +0000159
Hanno Beckerd6028a12018-10-15 12:01:35 +0100160#define SHR(x,n) (((x) & 0xFFFFFFFF) >> (n))
161#define ROTR(x,n) (SHR(x,n) | ((x) << (32 - (n))))
Paul Bakker5121ce52009-01-03 21:22:43 +0000162
163#define S0(x) (ROTR(x, 7) ^ ROTR(x,18) ^ SHR(x, 3))
164#define S1(x) (ROTR(x,17) ^ ROTR(x,19) ^ SHR(x,10))
165
166#define S2(x) (ROTR(x, 2) ^ ROTR(x,13) ^ ROTR(x,22))
167#define S3(x) (ROTR(x, 6) ^ ROTR(x,11) ^ ROTR(x,25))
168
Hanno Beckerd6028a12018-10-15 12:01:35 +0100169#define F0(x,y,z) (((x) & (y)) | ((z) & ((x) | (y))))
170#define F1(x,y,z) ((z) ^ ((x) & ((y) ^ (z))))
Paul Bakker5121ce52009-01-03 21:22:43 +0000171
172#define R(t) \
Hanno Beckerd6028a12018-10-15 12:01:35 +0100173 ( \
174 W[t] = S1(W[(t) - 2]) + W[(t) - 7] + \
175 S0(W[(t) - 15]) + W[(t) - 16] \
176 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000177
Hanno Beckerd6028a12018-10-15 12:01:35 +0100178#define P(a,b,c,d,e,f,g,h,x,K) \
179 do \
180 { \
Hanno Becker3ac21ac2018-10-26 09:13:26 +0100181 temp1 = (h) + S3(e) + F1((e),(f),(g)) + (K) + (x); \
182 temp2 = S2(a) + F0((a),(b),(c)); \
Hanno Beckerd6028a12018-10-15 12:01:35 +0100183 (d) += temp1; (h) = temp1 + temp2; \
184 } while( 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000185
Andres Amaya Garciacccfe082017-06-28 10:36:39 +0100186int mbedtls_internal_sha256_process( mbedtls_sha256_context *ctx,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100187 const unsigned char data[64] )
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200188{
189 uint32_t temp1, temp2, W[64];
190 uint32_t A[8];
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400191 uint32_t flow_ctrl = 0;
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200192 unsigned int i;
Paul Bakker5121ce52009-01-03 21:22:43 +0000193
Hanno Becker8d215e72018-12-18 17:53:21 +0000194 SHA256_VALIDATE_RET( ctx != NULL );
195 SHA256_VALIDATE_RET( (const unsigned char *)data != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +0000196
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200197 for( i = 0; i < 8; i++ )
198 A[i] = ctx->state[i];
199
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200200#if defined(MBEDTLS_SHA256_SMALLER)
Jarno Lamsabb86c522020-01-07 13:33:45 +0200201 {
202 uint32_t offset = mbedtls_platform_random_in_range(16);
203 mbedtls_platform_memset( W, 0, sizeof( W ) );
204
205 for( i = offset; i < 16; i++ )
206 {
207 W[i] = (uint32_t)mbedtls_platform_get_uint32_be( &data[4 * i] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400208 flow_ctrl++;
Jarno Lamsabb86c522020-01-07 13:33:45 +0200209 }
210 for( i = 0; i < offset; i++ )
211 {
212 W[i] = (uint32_t)mbedtls_platform_get_uint32_be( &data[4 * i] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400213 flow_ctrl++;
Jarno Lamsabb86c522020-01-07 13:33:45 +0200214 }
215 }
216
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400217 if( flow_ctrl != 16 )
218 {
219 return MBEDTLS_ERR_PLATFORM_FAULT_DETECTED;
220 }
221
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200222 for( i = 0; i < 64; i++ )
223 {
Jarno Lamsabb86c522020-01-07 13:33:45 +0200224 if( i >= 16 )
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200225 R( i );
226
227 P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i], K[i] );
228
229 temp1 = A[7]; A[7] = A[6]; A[6] = A[5]; A[5] = A[4]; A[4] = A[3];
230 A[3] = A[2]; A[2] = A[1]; A[1] = A[0]; A[0] = temp1;
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400231 flow_ctrl++;
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200232 }
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400233
234 if( flow_ctrl != 80 )
235 {
236 return MBEDTLS_ERR_PLATFORM_FAULT_DETECTED;
237 }
238
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200239#else /* MBEDTLS_SHA256_SMALLER */
240 for( i = 0; i < 16; i++ )
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400241 {
Arto Kinnunen4f4849a2019-09-09 10:21:18 +0300242 W[i] = (uint32_t)mbedtls_platform_get_uint32_be( &data[4 * i] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400243 flow_ctrl++;
244 }
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200245
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200246 for( i = 0; i < 16; i += 8 )
247 {
248 P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i+0], K[i+0] );
249 P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], W[i+1], K[i+1] );
250 P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], W[i+2], K[i+2] );
251 P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], W[i+3], K[i+3] );
252 P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], W[i+4], K[i+4] );
253 P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], W[i+5], K[i+5] );
254 P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], W[i+6], K[i+6] );
255 P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], W[i+7], K[i+7] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400256 flow_ctrl++;
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200257 }
258
259 for( i = 16; i < 64; i += 8 )
260 {
261 P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], R(i+0), K[i+0] );
262 P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], R(i+1), K[i+1] );
263 P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], R(i+2), K[i+2] );
264 P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], R(i+3), K[i+3] );
265 P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], R(i+4), K[i+4] );
266 P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], R(i+5), K[i+5] );
267 P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], R(i+6), K[i+6] );
268 P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], R(i+7), K[i+7] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400269 flow_ctrl++;
270 }
271
272 /* 16 from the first loop, 2 from the second and 6 from the third. */
273 if( flow_ctrl != 24 )
274 {
275 return MBEDTLS_ERR_PLATFORM_FAULT_DETECTED;
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200276 }
Manuel Pégourié-Gonnardeb0d8702015-05-28 12:54:04 +0200277#endif /* MBEDTLS_SHA256_SMALLER */
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400278 flow_ctrl = 0;
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200279
280 for( i = 0; i < 8; i++ )
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400281 {
Manuel Pégourié-Gonnarda7a3a5f2015-05-28 12:14:49 +0200282 ctx->state[i] += A[i];
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400283 flow_ctrl++;
284 }
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100285
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400286 if( flow_ctrl == 8 )
287 {
288 return( 0 );
289 }
Andrzej Kurekca609372020-07-08 03:19:02 -0400290 /* Free the ctx upon suspected FI */
291 mbedtls_sha256_free( ctx );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400292 return( MBEDTLS_ERR_PLATFORM_FAULT_DETECTED );
Paul Bakker5121ce52009-01-03 21:22:43 +0000293}
Jaeden Amero041039f2018-02-19 15:28:08 +0000294
295#if !defined(MBEDTLS_DEPRECATED_REMOVED)
296void mbedtls_sha256_process( mbedtls_sha256_context *ctx,
297 const unsigned char data[64] )
298{
299 mbedtls_internal_sha256_process( ctx, data );
300}
301#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200302#endif /* !MBEDTLS_SHA256_PROCESS_ALT */
Paul Bakker5121ce52009-01-03 21:22:43 +0000303
304/*
305 * SHA-256 process buffer
306 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100307int mbedtls_sha256_update_ret( mbedtls_sha256_context *ctx,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100308 const unsigned char *input,
309 size_t ilen )
Paul Bakker5121ce52009-01-03 21:22:43 +0000310{
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100311 int ret;
Paul Bakker23986e52011-04-24 08:57:21 +0000312 size_t fill;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000313 uint32_t left;
Andrzej Kurek74f7d0f2020-07-06 14:28:12 -0400314 volatile const unsigned char *input_dup = input;
315 volatile size_t ilen_dup = ilen;
316 size_t ilen_change;
Hanno Becker8d215e72018-12-18 17:53:21 +0000317 SHA256_VALIDATE_RET( ctx != NULL );
318 SHA256_VALIDATE_RET( ilen == 0 || input != NULL );
Hanno Becker596e0142018-12-18 15:00:38 +0000319
Brian White12895d12014-04-11 11:29:42 -0400320 if( ilen == 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100321 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000322
323 left = ctx->total[0] & 0x3F;
324 fill = 64 - left;
325
Paul Bakker5c2364c2012-10-01 14:41:15 +0000326 ctx->total[0] += (uint32_t) ilen;
Paul Bakker5121ce52009-01-03 21:22:43 +0000327 ctx->total[0] &= 0xFFFFFFFF;
328
Paul Bakker5c2364c2012-10-01 14:41:15 +0000329 if( ctx->total[0] < (uint32_t) ilen )
Paul Bakker5121ce52009-01-03 21:22:43 +0000330 ctx->total[1]++;
331
332 if( left && ilen >= fill )
333 {
Teppo Järvelin91d79382019-10-02 09:09:31 +0300334 mbedtls_platform_memcpy( (void *) (ctx->buffer + left), input, fill );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100335
Andres Amaya Garciacccfe082017-06-28 10:36:39 +0100336 if( ( ret = mbedtls_internal_sha256_process( ctx, ctx->buffer ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100337 return( ret );
338
Paul Bakker5121ce52009-01-03 21:22:43 +0000339 input += fill;
340 ilen -= fill;
341 left = 0;
342 }
343
344 while( ilen >= 64 )
345 {
Andres Amaya Garciacccfe082017-06-28 10:36:39 +0100346 if( ( ret = mbedtls_internal_sha256_process( ctx, input ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100347 return( ret );
348
Paul Bakker5121ce52009-01-03 21:22:43 +0000349 input += 64;
350 ilen -= 64;
351 }
352
353 if( ilen > 0 )
Teppo Järvelin91d79382019-10-02 09:09:31 +0300354 mbedtls_platform_memcpy( (void *) (ctx->buffer + left), input, ilen );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100355
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400356 /* Re-check ilen to protect from a FI attack */
357 if( ilen < 64 )
358 {
Andrzej Kurek74f7d0f2020-07-06 14:28:12 -0400359 /* Re-check that the calculated offsets are correct */
360 ilen_change = ilen_dup - ilen;
361 if( ( input_dup + ilen_change ) == input )
362 {
363 return( 0 );
364 }
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400365 }
Andrzej Kurekca609372020-07-08 03:19:02 -0400366 /* Free the ctx upon suspected FI */
367 mbedtls_sha256_free( ctx );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400368 return( MBEDTLS_ERR_PLATFORM_FAULT_DETECTED );
Paul Bakker5121ce52009-01-03 21:22:43 +0000369}
370
Jaeden Amero041039f2018-02-19 15:28:08 +0000371#if !defined(MBEDTLS_DEPRECATED_REMOVED)
372void mbedtls_sha256_update( mbedtls_sha256_context *ctx,
373 const unsigned char *input,
374 size_t ilen )
375{
376 mbedtls_sha256_update_ret( ctx, input, ilen );
377}
378#endif
379
Paul Bakker5121ce52009-01-03 21:22:43 +0000380/*
381 * SHA-256 final digest
382 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100383int mbedtls_sha256_finish_ret( mbedtls_sha256_context *ctx,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100384 unsigned char output[32] )
Paul Bakker5121ce52009-01-03 21:22:43 +0000385{
Arto Kinnunen9b3b1942019-09-09 17:02:35 +0300386 int ret, s_pos, o_pos;
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200387 uint32_t used;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000388 uint32_t high, low;
Jarno Lamsabb86c522020-01-07 13:33:45 +0200389 uint32_t offset = 0;
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400390 uint32_t flow_ctrl = 0;
Paul Bakker5121ce52009-01-03 21:22:43 +0000391
Hanno Becker8d215e72018-12-18 17:53:21 +0000392 SHA256_VALIDATE_RET( ctx != NULL );
393 SHA256_VALIDATE_RET( (unsigned char *)output != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +0000394
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200395 /*
396 * Add padding: 0x80 then 0x00 until 8 bytes remain for the length
397 */
398 used = ctx->total[0] & 0x3F;
399
400 ctx->buffer[used++] = 0x80;
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400401 flow_ctrl++;
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200402
403 if( used <= 56 )
404 {
405 /* Enough room for padding + length in current block */
Manuel Pégourié-Gonnard7a346b82019-10-02 14:47:01 +0200406 mbedtls_platform_memset( ctx->buffer + used, 0, 56 - used );
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200407 }
408 else
409 {
410 /* We'll need an extra block */
Manuel Pégourié-Gonnard7a346b82019-10-02 14:47:01 +0200411 mbedtls_platform_memset( ctx->buffer + used, 0, 64 - used );
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200412
413 if( ( ret = mbedtls_internal_sha256_process( ctx, ctx->buffer ) ) != 0 )
414 return( ret );
415
Manuel Pégourié-Gonnard7a346b82019-10-02 14:47:01 +0200416 mbedtls_platform_memset( ctx->buffer, 0, 56 );
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200417 }
418
419 /*
420 * Add message length
421 */
Paul Bakker5121ce52009-01-03 21:22:43 +0000422 high = ( ctx->total[0] >> 29 )
423 | ( ctx->total[1] << 3 );
424 low = ( ctx->total[0] << 3 );
425
Arto Kinnunen3d7439e2019-09-10 11:30:40 +0300426 (void)mbedtls_platform_put_uint32_be( ctx->buffer + 56, high );
427 (void)mbedtls_platform_put_uint32_be( ctx->buffer + 60, low );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400428 flow_ctrl++;
Paul Bakker5121ce52009-01-03 21:22:43 +0000429
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200430 if( ( ret = mbedtls_internal_sha256_process( ctx, ctx->buffer ) ) != 0 )
Andres Amaya Garciaaa464ef2017-07-21 14:21:53 +0100431 return( ret );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100432
Manuel Pégourié-Gonnard1cc1fb02018-06-28 12:10:27 +0200433 /*
434 * Output final state
435 */
Jarno Lamsabb86c522020-01-07 13:33:45 +0200436 offset = mbedtls_platform_random_in_range(7);
Arto Kinnunen0b62ce82019-09-04 14:04:57 +0300437
Jarno Lamsabb86c522020-01-07 13:33:45 +0200438 mbedtls_platform_memset( output, 0, 32 );
439
440 for( s_pos = offset, o_pos = offset * 4; s_pos < 7;
441 s_pos++, o_pos += 4 )
Arto Kinnunen0b62ce82019-09-04 14:04:57 +0300442 {
Arto Kinnunen3d7439e2019-09-10 11:30:40 +0300443 (void)mbedtls_platform_put_uint32_be( &output[o_pos],
Jarno Lamsabb86c522020-01-07 13:33:45 +0200444 ctx->state[s_pos] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400445 flow_ctrl++;
Arto Kinnunen0b62ce82019-09-04 14:04:57 +0300446 }
Paul Bakker5121ce52009-01-03 21:22:43 +0000447
Manuel Pégourié-Gonnard8463d292019-07-16 14:39:55 +0200448#if !defined(MBEDTLS_SHA256_NO_SHA224)
Paul Bakker5121ce52009-01-03 21:22:43 +0000449 if( ctx->is224 == 0 )
Manuel Pégourié-Gonnard8463d292019-07-16 14:39:55 +0200450#endif
Arto Kinnunen3d7439e2019-09-10 11:30:40 +0300451 (void)mbedtls_platform_put_uint32_be( &output[28], ctx->state[7] );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100452
Jarno Lamsabb86c522020-01-07 13:33:45 +0200453 for( s_pos = 0, o_pos = 0; s_pos < (int)offset; s_pos++, o_pos += 4 )
454 {
455 (void)mbedtls_platform_put_uint32_be( &output[o_pos],
456 ctx->state[s_pos] );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400457 flow_ctrl++;
Jarno Lamsabb86c522020-01-07 13:33:45 +0200458 }
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400459 /* flow ctrl was incremented twice and then 7 times in two loops */
460 if( flow_ctrl == 9 )
461 {
462 return( 0 );
463 }
Andrzej Kurekca609372020-07-08 03:19:02 -0400464 /* Free the ctx and clear output upon suspected FI */
465 mbedtls_sha256_free( ctx );
466 mbedtls_platform_memset( output, 0, 32 );
Andrzej Kurek78f77eb2020-06-04 08:09:53 -0400467 return( MBEDTLS_ERR_PLATFORM_FAULT_DETECTED );
Paul Bakker5121ce52009-01-03 21:22:43 +0000468}
469
Jaeden Amero041039f2018-02-19 15:28:08 +0000470#if !defined(MBEDTLS_DEPRECATED_REMOVED)
471void mbedtls_sha256_finish( mbedtls_sha256_context *ctx,
472 unsigned char output[32] )
473{
474 mbedtls_sha256_finish_ret( ctx, output );
475}
476#endif
477
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200478#endif /* !MBEDTLS_SHA256_ALT */
Paul Bakker90995b52013-06-24 19:20:35 +0200479
Paul Bakker5121ce52009-01-03 21:22:43 +0000480/*
481 * output = SHA-256( input buffer )
482 */
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100483int mbedtls_sha256_ret( const unsigned char *input,
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100484 size_t ilen,
485 unsigned char output[32],
486 int is224 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000487{
Andrzej Kurek74f7d0f2020-07-06 14:28:12 -0400488 int ret = MBEDTLS_ERR_PLATFORM_FAULT_DETECTED;
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200489 mbedtls_sha256_context ctx;
Andrzej Kurek74f7d0f2020-07-06 14:28:12 -0400490 volatile const unsigned char *input_dup = input;
491 volatile size_t ilen_dup = ilen;
Paul Bakker5121ce52009-01-03 21:22:43 +0000492
Hanno Becker8d215e72018-12-18 17:53:21 +0000493 SHA256_VALIDATE_RET( is224 == 0 || is224 == 1 );
494 SHA256_VALIDATE_RET( ilen == 0 || input != NULL );
495 SHA256_VALIDATE_RET( (unsigned char *)output != NULL );
Andres Amaya Garcia79e593f2018-12-09 20:41:20 +0000496
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200497 mbedtls_sha256_init( &ctx );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100498
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100499 if( ( ret = mbedtls_sha256_starts_ret( &ctx, is224 ) ) != 0 )
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100500 goto exit;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100501
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100502 if( ( ret = mbedtls_sha256_update_ret( &ctx, input, ilen ) ) != 0 )
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100503 goto exit;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100504
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100505 if( ( ret = mbedtls_sha256_finish_ret( &ctx, output ) ) != 0 )
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100506 goto exit;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100507
Andres Amaya Garcia0963e6c2017-07-20 14:34:08 +0100508exit:
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200509 mbedtls_sha256_free( &ctx );
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100510
Andrzej Kurek74f7d0f2020-07-06 14:28:12 -0400511 if( input_dup == input && ilen_dup == ilen )
512 {
513 return( ret );
514 }
Andrzej Kurekca609372020-07-08 03:19:02 -0400515 mbedtls_platform_memset( output, 0, 32 );
Andrzej Kurek74f7d0f2020-07-06 14:28:12 -0400516 return( MBEDTLS_ERR_PLATFORM_FAULT_DETECTED );
Paul Bakker5121ce52009-01-03 21:22:43 +0000517}
518
Jaeden Amero041039f2018-02-19 15:28:08 +0000519#if !defined(MBEDTLS_DEPRECATED_REMOVED)
520void mbedtls_sha256( const unsigned char *input,
521 size_t ilen,
522 unsigned char output[32],
523 int is224 )
524{
525 mbedtls_sha256_ret( input, ilen, output, is224 );
526}
527#endif
528
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200529#if defined(MBEDTLS_SELF_TEST)
Paul Bakker5121ce52009-01-03 21:22:43 +0000530/*
531 * FIPS-180-2 test vectors
532 */
Manuel Pégourié-Gonnard28122e42015-03-11 09:13:42 +0000533static const unsigned char sha256_test_buf[3][57] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000534{
535 { "abc" },
536 { "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" },
537 { "" }
538};
539
Andres Amaya Garcia2d0aa8b2017-07-21 14:57:26 +0100540static const size_t sha256_test_buflen[3] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000541{
542 3, 56, 1000
543};
544
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200545static const unsigned char sha256_test_sum[][32] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000546{
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200547#if !defined(MBEDTLS_SHA256_NO_SHA224)
Paul Bakker5121ce52009-01-03 21:22:43 +0000548 /*
549 * SHA-224 test vectors
550 */
551 { 0x23, 0x09, 0x7D, 0x22, 0x34, 0x05, 0xD8, 0x22,
552 0x86, 0x42, 0xA4, 0x77, 0xBD, 0xA2, 0x55, 0xB3,
553 0x2A, 0xAD, 0xBC, 0xE4, 0xBD, 0xA0, 0xB3, 0xF7,
554 0xE3, 0x6C, 0x9D, 0xA7 },
555 { 0x75, 0x38, 0x8B, 0x16, 0x51, 0x27, 0x76, 0xCC,
556 0x5D, 0xBA, 0x5D, 0xA1, 0xFD, 0x89, 0x01, 0x50,
557 0xB0, 0xC6, 0x45, 0x5C, 0xB4, 0xF5, 0x8B, 0x19,
558 0x52, 0x52, 0x25, 0x25 },
559 { 0x20, 0x79, 0x46, 0x55, 0x98, 0x0C, 0x91, 0xD8,
560 0xBB, 0xB4, 0xC1, 0xEA, 0x97, 0x61, 0x8A, 0x4B,
561 0xF0, 0x3F, 0x42, 0x58, 0x19, 0x48, 0xB2, 0xEE,
562 0x4E, 0xE7, 0xAD, 0x67 },
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200563#endif /* !MBEDTLS_SHA256_NO_SHA224 */
Paul Bakker5121ce52009-01-03 21:22:43 +0000564
565 /*
566 * SHA-256 test vectors
567 */
568 { 0xBA, 0x78, 0x16, 0xBF, 0x8F, 0x01, 0xCF, 0xEA,
569 0x41, 0x41, 0x40, 0xDE, 0x5D, 0xAE, 0x22, 0x23,
570 0xB0, 0x03, 0x61, 0xA3, 0x96, 0x17, 0x7A, 0x9C,
571 0xB4, 0x10, 0xFF, 0x61, 0xF2, 0x00, 0x15, 0xAD },
572 { 0x24, 0x8D, 0x6A, 0x61, 0xD2, 0x06, 0x38, 0xB8,
573 0xE5, 0xC0, 0x26, 0x93, 0x0C, 0x3E, 0x60, 0x39,
574 0xA3, 0x3C, 0xE4, 0x59, 0x64, 0xFF, 0x21, 0x67,
575 0xF6, 0xEC, 0xED, 0xD4, 0x19, 0xDB, 0x06, 0xC1 },
576 { 0xCD, 0xC7, 0x6E, 0x5C, 0x99, 0x14, 0xFB, 0x92,
577 0x81, 0xA1, 0xC7, 0xE2, 0x84, 0xD7, 0x3E, 0x67,
578 0xF1, 0x80, 0x9A, 0x48, 0xA4, 0x97, 0x20, 0x0E,
579 0x04, 0x6D, 0x39, 0xCC, 0xC7, 0x11, 0x2C, 0xD0 }
580};
581
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200582#define SHA256_TEST_SUM_N \
583 ( sizeof( sha256_test_sum ) / sizeof( sha256_test_sum[0] ) )
584
Paul Bakker5121ce52009-01-03 21:22:43 +0000585/*
Paul Bakker5121ce52009-01-03 21:22:43 +0000586 * Checkup routine
587 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200588int mbedtls_sha256_self_test( int verbose )
Paul Bakker5121ce52009-01-03 21:22:43 +0000589{
Paul Bakker5b4af392014-06-26 12:09:34 +0200590 int i, j, k, buflen, ret = 0;
Russ Butlerbb83b422016-10-12 17:36:50 -0500591 unsigned char *buf;
Paul Bakker9e36f042013-06-30 14:34:05 +0200592 unsigned char sha256sum[32];
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200593 mbedtls_sha256_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +0000594
Russ Butlerbb83b422016-10-12 17:36:50 -0500595 buf = mbedtls_calloc( 1024, sizeof(unsigned char) );
596 if( NULL == buf )
597 {
598 if( verbose != 0 )
599 mbedtls_printf( "Buffer allocation failed\n" );
600
601 return( 1 );
602 }
603
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200604 mbedtls_sha256_init( &ctx );
Paul Bakker5b4af392014-06-26 12:09:34 +0200605
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200606 for( i = 0; i < (int) SHA256_TEST_SUM_N; i++ )
Paul Bakker5121ce52009-01-03 21:22:43 +0000607 {
608 j = i % 3;
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200609#if !defined(MBEDTLS_SHA256_NO_SHA224)
Paul Bakker5121ce52009-01-03 21:22:43 +0000610 k = i < 3;
Manuel Pégourié-Gonnardabebdd12019-07-16 15:37:56 +0200611#else
612 k = 0;
613#endif
Paul Bakker5121ce52009-01-03 21:22:43 +0000614
615 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200616 mbedtls_printf( " SHA-%d test #%d: ", 256 - k * 32, j + 1 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000617
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100618 if( ( ret = mbedtls_sha256_starts_ret( &ctx, k ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100619 goto fail;
Paul Bakker5121ce52009-01-03 21:22:43 +0000620
621 if( j == 2 )
622 {
Teppo Järvelind49d2b62019-10-30 13:48:12 +0200623 memset( buf, 'a', buflen = 1000 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000624
625 for( j = 0; j < 1000; j++ )
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100626 {
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100627 ret = mbedtls_sha256_update_ret( &ctx, buf, buflen );
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100628 if( ret != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100629 goto fail;
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100630 }
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100631
Paul Bakker5121ce52009-01-03 21:22:43 +0000632 }
633 else
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100634 {
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100635 ret = mbedtls_sha256_update_ret( &ctx, sha256_test_buf[j],
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100636 sha256_test_buflen[j] );
637 if( ret != 0 )
638 goto fail;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100639 }
Paul Bakker5121ce52009-01-03 21:22:43 +0000640
Gilles Peskine9e4f77c2018-01-22 11:48:08 +0100641 if( ( ret = mbedtls_sha256_finish_ret( &ctx, sha256sum ) ) != 0 )
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100642 goto fail;
643
Paul Bakker5121ce52009-01-03 21:22:43 +0000644
Paul Bakker9e36f042013-06-30 14:34:05 +0200645 if( memcmp( sha256sum, sha256_test_sum[i], 32 - k * 4 ) != 0 )
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100646 {
647 ret = 1;
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100648 goto fail;
Andres Amaya Garcia6a3f3052017-07-20 14:18:54 +0100649 }
Paul Bakker5121ce52009-01-03 21:22:43 +0000650
651 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200652 mbedtls_printf( "passed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000653 }
654
655 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200656 mbedtls_printf( "\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +0000657
Andres Amaya Garcia72a7f532017-05-02 11:38:47 +0100658 goto exit;
659
660fail:
661 if( verbose != 0 )
662 mbedtls_printf( "failed\n" );
663
Paul Bakker5b4af392014-06-26 12:09:34 +0200664exit:
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200665 mbedtls_sha256_free( &ctx );
Russ Butlerbb83b422016-10-12 17:36:50 -0500666 mbedtls_free( buf );
Paul Bakker5b4af392014-06-26 12:09:34 +0200667
668 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +0000669}
670
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200671#endif /* MBEDTLS_SELF_TEST */
Paul Bakker5121ce52009-01-03 21:22:43 +0000672
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200673#endif /* MBEDTLS_SHA256_C */