Coverage Report

Created: 2026-11-12 06:59

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/wolfssl-normal-math/wolfcrypt/src/sha256.c
Line
Count
Source
1
/* sha256.c
2
 *
3
 * Copyright (C) 2006-2026 wolfSSL Inc.
4
 *
5
 * This file is part of wolfSSL.
6
 *
7
 * wolfSSL is free software; you can redistribute it and/or modify
8
 * it under the terms of the GNU General Public License as published by
9
 * the Free Software Foundation; either version 3 of the License, or
10
 * (at your option) any later version.
11
 *
12
 * wolfSSL is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
 * GNU General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU General Public License
18
 * along with this program; if not, write to the Free Software
19
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
20
 */
21
22
/* For more info on the algorithm, see https://tools.ietf.org/html/rfc6234
23
 *
24
 * For more information on NIST FIPS PUB 180-4, see
25
 * https://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.180-4.pdf
26
 */
27
28
/*
29
30
DESCRIPTION
31
This library provides the interface to SHA-256 secure hash algorithms.
32
SHA-256 performs processing on message blocks to produce a final hash digest
33
output. It can be used to hash a message, M, having a length of L bits,
34
where 0 <= L < 2^64.
35
36
Note that in some cases, hardware acceleration may be enabled, depending
37
on the specific device platform.
38
39
*/
40
41
#define WC_FIPS_LL_CRYPTO
42
#define _WC_BUILDING_SHA256_C
43
44
#include <wolfssl/wolfcrypt/libwolfssl_sources.h>
45
46
/*
47
 * SHA256 Build Options:
48
 * USE_SLOW_SHA256:            Reduces code size by not partially unrolling
49
                                (~2KB smaller and ~25% slower) (default OFF)
50
 * WOLFSSL_SHA256_BY_SPEC:     Uses the Ch/Maj based on SHA256 specification
51
                                (default ON)
52
 * WOLFSSL_SHA256_ALT_CH_MAJ:  Alternate Ch/Maj that is easier for compilers to
53
                                optimize and recognize as SHA256 (default OFF)
54
 * SHA256_MANY_REGISTERS:      A SHA256 version that keeps all data in registers
55
                                and partial unrolled (default OFF)
56
 */
57
58
/* Default SHA256 to use Ch/Maj based on specification */
59
#if !defined(WOLFSSL_SHA256_BY_SPEC) && !defined(WOLFSSL_SHA256_ALT_CH_MAJ)
60
    #define WOLFSSL_SHA256_BY_SPEC
61
#endif
62
63
64
#if !defined(NO_SHA256)
65
66
#if defined(HAVE_FIPS) && defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)
67
    #if defined(USE_WINDOWS_API) && defined(_MSC_VER)
68
        #pragma code_seg(".fipsA$l")
69
        #pragma const_seg(".fipsB$l")
70
    #endif
71
#endif
72
73
#include <wolfssl/wolfcrypt/sha256.h>
74
#include <wolfssl/wolfcrypt/cpuid.h>
75
#include <wolfssl/wolfcrypt/hash.h>
76
77
#ifdef WOLF_CRYPTO_CB
78
    #include <wolfssl/wolfcrypt/cryptocb.h>
79
#endif
80
81
#ifdef WOLFSSL_IMXRT1170_CAAM
82
    #include <wolfssl/wolfcrypt/port/caam/wolfcaam_fsl_nxp.h>
83
#endif
84
85
86
/* determine if we are using Espressif SHA hardware acceleration */
87
#undef WOLFSSL_USE_ESP32_CRYPT_HASH_HW
88
#if defined(WOLFSSL_ESP32_CRYPT) && \
89
    !defined(NO_WOLFSSL_ESP32_CRYPT_HASH)
90
    /* define a single keyword for simplicity & readability
91
     *
92
     * by default the HW acceleration is on for ESP32-WROOM32
93
     * but individual components can be turned off.
94
     */
95
    #define WOLFSSL_USE_ESP32_CRYPT_HASH_HW
96
#else
97
    #undef WOLFSSL_USE_ESP32_CRYPT_HASH_HW
98
#endif
99
100
/* WOLF_CRYPTO_CB_ONLY_SHA256 strips the software SHA-256 implementation and
101
 * routes every operation through the crypto callback. It is mutually exclusive
102
 * with any in-tree SHA-256 hardware/asm backend below: keep this list in sync
103
 * with the #elif chain at the start of the "Hardware Acceleration" section. */
104
#if defined(WOLF_CRYPTO_CB_ONLY_SHA256) && ( \
105
        defined(WOLFSSL_TI_HASH) || \
106
        defined(MAX3266X_SHA) || \
107
        defined(FREESCALE_LTC_SHA) || \
108
        defined(FREESCALE_MMCAU_SHA) || \
109
        defined(WOLFSSL_PIC32MZ_HASH) || \
110
        defined(STM32_HASH_SHA2) || \
111
        (defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_HASH)) || \
112
        (defined(WOLFSSL_SE050) && defined(WOLFSSL_SE050_HASH)) || \
113
        defined(WOLFSSL_AFALG_HASH) || \
114
        defined(WOLFSSL_DEVCRYPTO_HASH) || \
115
        (defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_HASH)) || \
116
        defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) || \
117
        defined(WOLFSSL_RENESAS_TSIP_TLS) || \
118
        defined(WOLFSSL_RENESAS_SCEPROTECT) || \
119
        defined(WOLFSSL_RENESAS_RSIP) || \
120
        defined(PSOC6_HASH_SHA2) || \
121
        defined(WOLFSSL_IMXRT_DCP) || \
122
        defined(WOLFSSL_NXP_HASHCRYPT_SHA) || \
123
        defined(WOLFSSL_SILABS_SE_ACCEL) || \
124
        defined(WOLFSSL_KCAPI_HASH) || \
125
        (defined(WOLFSSL_HAVE_PSA) && !defined(WOLFSSL_PSA_NO_HASH)) || \
126
        defined(WOLFSSL_RENESAS_RX64_HASH) || \
127
        defined(WOLFSSL_PPC32_ASM) || \
128
        defined(WOLFSSL_PPC64_ASM) || \
129
        defined(WOLFSSL_ARMASM) || \
130
        defined(WOLFSSL_RISCV_ASM) || \
131
        (defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
132
            (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))))
133
    #error "WOLF_CRYPTO_CB_ONLY_SHA256 is incompatible with SHA-256 hardware" \
134
           " acceleration backends"
135
#endif
136
137
#ifdef WOLFSSL_ESPIDF
138
    /* Define the ESP_LOGx(TAG,  WOLFSSL_ESPIDF_BLANKLINE_MESSAGE value for output messages here.
139
    **
140
    ** Beware of possible conflict in test.c (that one now named TEST_TAG)
141
    */
142
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
143
       !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
144
        static const char* TAG = "wc_sha256";
145
    #endif
146
#endif
147
148
#if defined(WOLFSSL_HAVE_SHA256_HASH_BLOCK) && \
149
    (defined(WOLFSSL_TI_HASH) || defined(WOLFSSL_CRYPTOCELL) || \
150
     defined(MAX3266X_SHA) || defined(WOLFSSL_KCAPI_HASH))
151
    #error "WOLFSSL_HAVE_SHA256_HASH_BLOCK set without a SHA-256 transform"
152
#endif
153
154
#if defined(WOLFSSL_TI_HASH)
155
    /* #include <wolfcrypt/src/port/ti/ti-hash.c> included by wc_port.c */
156
#elif defined(MAX3266X_SHA)
157
    /* Already brought in by sha256.h */
158
    /* #include <wolfssl/wolfcrypt/port/maxim/max3266x.h> */
159
#else
160
161
#ifdef NO_INLINE
162
    #include <wolfssl/wolfcrypt/misc.h>
163
#else
164
    #define WOLFSSL_MISC_INCLUDED
165
    #include <wolfcrypt/src/misc.c>
166
#endif
167
168
#ifdef WOLFSSL_DEVCRYPTO_HASH
169
    #include <wolfssl/wolfcrypt/port/devcrypto/wc_devcrypto.h>
170
#endif
171
#if defined(WOLFSSL_SE050) && defined(WOLFSSL_SE050_HASH)
172
    #include <wolfssl/wolfcrypt/port/nxp/se050_port.h>
173
#endif
174
175
#if FIPS_VERSION3_GE(6,0,0)
176
    const unsigned int wolfCrypt_FIPS_sha256_ro_sanity[2] =
177
                                                     { 0x1a2b3c4d, 0x00000014 };
178
    int wolfCrypt_FIPS_SHA256_sanity(void)
179
    {
180
        return 0;
181
    }
182
#endif
183
184
#if defined(WC_C_DYNAMIC_FALLBACK) && \
185
        defined(WOLFSSL_AESNI) && !defined(USE_INTEL_SPEEDUP)
186
    /* AES-NI can be enabled with WC_C_DYNAMIC_FALLBACK, but without the rest of
187
     * USE_INTEL_SPEEDUP, in which case we need to disable the dynamic
188
     * fallback.
189
     */
190
    #undef WC_C_DYNAMIC_FALLBACK
191
#endif
192
193
#if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP)
194
    #if defined(__GNUC__) && ((__GNUC__ < 4) || \
195
                              (__GNUC__ == 4 && __GNUC_MINOR__ <= 8))
196
        #undef  NO_AVX2_SUPPORT
197
        #define NO_AVX2_SUPPORT
198
    #endif
199
    #if defined(__clang__) && ((__clang_major__ < 3) || \
200
                               (__clang_major__ == 3 && __clang_minor__ <= 5))
201
        #define NO_AVX2_SUPPORT
202
    #elif defined(__clang__) && defined(NO_AVX2_SUPPORT)
203
        #undef NO_AVX2_SUPPORT
204
    #endif
205
206
    #define HAVE_INTEL_AVX1
207
    #ifndef NO_AVX2_SUPPORT
208
        #define HAVE_INTEL_AVX2
209
    #endif
210
#else
211
    #undef HAVE_INTEL_AVX1
212
    #undef HAVE_INTEL_AVX2
213
#endif /* WOLFSSL_X86_64_BUILD && USE_INTEL_SPEEDUP */
214
215
#if defined(HAVE_INTEL_AVX2)
216
    #define HAVE_INTEL_RORX
217
#endif
218
219
#if defined(LITTLE_ENDIAN_ORDER)
220
    #if ( defined(CONFIG_IDF_TARGET_ESP32C2) || \
221
          defined(CONFIG_IDF_TARGET_ESP8684) || \
222
          defined(CONFIG_IDF_TARGET_ESP32C3) || \
223
          defined(CONFIG_IDF_TARGET_ESP32C6)    \
224
        ) && \
225
        defined(WOLFSSL_ESP32_CRYPT) &&         \
226
        !defined(NO_WOLFSSL_ESP32_CRYPT_HASH) && \
227
        !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
228
        /* For Espressif RISC-V Targets, we *may* need to reverse bytes
229
         * depending on if HW is active or not. */
230
        #define SHA256_REV_BYTES(ctx) \
231
            (esp_sha_need_byte_reversal(ctx))
232
    #elif defined(FREESCALE_MMCAU_SHA)
233
        #define SHA256_REV_BYTES(ctx)       1 /* reverse needed on final */
234
    #endif
235
#endif
236
#ifndef SHA256_REV_BYTES
237
    #if defined(LITTLE_ENDIAN_ORDER) || defined(WOLFSSL_WIDE_BYTE)
238
893k
        #define SHA256_REV_BYTES(ctx)       1
239
    #else
240
        #define SHA256_REV_BYTES(ctx)       0
241
    #endif
242
#endif
243
#if defined(LITTLE_ENDIAN_ORDER) && \
244
        defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
245
        (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))
246
247
    #if defined(WC_C_DYNAMIC_FALLBACK) && !defined(WC_NO_INTERNAL_FUNCTION_POINTERS)
248
        /* With the AVX backend, wc_Sha256.buffer is in big endian even though
249
         * the host is little endian.  For WC_C_DYNAMIC_FALLBACK, which requires
250
         * alternating between AVX and C, we activate
251
         * WC_NO_INTERNAL_FUNCTION_POINTERS, which arranges for just-in-time
252
         * byte swapping on each call to the C back end.  This keeps the buffers
253
         * big endian at all times.
254
         */
255
        #define WC_NO_INTERNAL_FUNCTION_POINTERS
256
    #endif
257
258
    #ifdef WC_NO_INTERNAL_FUNCTION_POINTERS
259
        /* With WC_NO_INTERNAL_FUNCTION_POINTERS every transform is dispatched
260
         * through inline_XTRANSFORM{,_LEN}(), whose C arm is
261
         * Transform_Sha256{,_Len}_C_from_raw() -- those byte-reverse the block
262
         * themselves, just in time.
263
         */
264
        #define WC_SHA256_RAW_BE_BUFFER
265
        #define SHA256_UPDATE_REV_BYTES(ctx) 0
266
    #else
267
        #define SHA256_UPDATE_REV_BYTES(ctx) \
268
            (!IS_INTEL_AVX1(intel_flags) && !IS_INTEL_AVX2(intel_flags) && \
269
             !IS_INTEL_SHA(intel_flags))
270
    #endif
271
#elif defined(FREESCALE_MMCAU_SHA)
272
    #define SHA256_UPDATE_REV_BYTES(ctx)    0 /* reverse not needed on update */
273
#elif defined(WOLFSSL_PPC32_ASM)
274
    #define SHA256_UPDATE_REV_BYTES(ctx)    0
275
#elif defined(WOLFSSL_PPC64_ASM)
276
    #define SHA256_UPDATE_REV_BYTES(ctx)    0
277
#elif defined(WOLFSSL_ARMASM)
278
    #define SHA256_UPDATE_REV_BYTES(ctx)    0
279
#elif defined(WOLFSSL_RISCV_ASM)
280
    #define SHA256_UPDATE_REV_BYTES(ctx)    0
281
#else
282
782k
    #define SHA256_UPDATE_REV_BYTES(ctx)    SHA256_REV_BYTES(ctx)
283
#endif
284
285
#if !defined(WOLFSSL_PIC32MZ_HASH) && !defined(STM32_HASH_SHA2) && \
286
    (!defined(WOLFSSL_IMX6_CAAM) || defined(NO_IMX6_CAAM_HASH) || \
287
     defined(WOLFSSL_QNX_CAAM)) && \
288
    !defined(WOLFSSL_AFALG_HASH) && !defined(WOLFSSL_DEVCRYPTO_HASH) && \
289
    (!defined(WOLFSSL_ESP32_CRYPT) || defined(NO_WOLFSSL_ESP32_CRYPT_HASH)) && \
290
    ((!defined(WOLFSSL_RENESAS_TSIP_TLS) && \
291
      !defined(WOLFSSL_RENESAS_TSIP_CRYPTONLY)) || \
292
     defined(NO_WOLFSSL_RENESAS_TSIP_CRYPT_HASH)) && \
293
    !defined(PSOC6_HASH_SHA2) && !defined(WOLFSSL_IMXRT_DCP) && !defined(WOLFSSL_SILABS_SE_ACCEL) && \
294
    !defined(WOLFSSL_NXP_HASHCRYPT_SHA) && \
295
    !defined(WOLFSSL_KCAPI_HASH) && !defined(WOLFSSL_SE050_HASH) && \
296
    ((!defined(WOLFSSL_RENESAS_SCEPROTECT) && \
297
      !defined(WOLFSSL_RENESAS_RSIP)) \
298
      || defined(NO_WOLFSSL_RENESAS_FSPSM_HASH)) && \
299
    (!defined(WOLFSSL_HAVE_PSA) || defined(WOLFSSL_PSA_NO_HASH)) && \
300
    !defined(WOLFSSL_RENESAS_RX64_HASH)
301
302
#if (defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
303
     (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))) || \
304
    (defined(WOLFSSL_ARMASM) && defined(__aarch64__) && \
305
     !defined(WOLF_CRYPTO_CB_ONLY_SHA256))
306
static void Sha256_SetTransform(void);
307
#endif
308
309
static int InitSha256(wc_Sha256* sha256)
310
237k
{
311
237k
    XMEMSET(sha256->digest, 0, sizeof(sha256->digest));
312
237k
    sha256->digest[0] = 0x6A09E667L;
313
237k
    sha256->digest[1] = 0xBB67AE85L;
314
237k
    sha256->digest[2] = 0x3C6EF372L;
315
237k
    sha256->digest[3] = 0xA54FF53AL;
316
237k
    sha256->digest[4] = 0x510E527FL;
317
237k
    sha256->digest[5] = 0x9B05688CL;
318
237k
    sha256->digest[6] = 0x1F83D9ABL;
319
237k
    sha256->digest[7] = 0x5BE0CD19L;
320
321
237k
    sha256->buffLen = 0;
322
237k
    XMEMSET(sha256->buffer, 0, sizeof(sha256->buffer));
323
237k
    sha256->loLen   = 0;
324
237k
    sha256->hiLen   = 0;
325
237k
#ifdef WOLFSSL_HASH_FLAGS
326
237k
    sha256->flags = 0;
327
237k
#endif
328
#ifdef WOLFSSL_HASH_KEEP
329
    sha256->msg  = NULL;
330
    sha256->len  = 0;
331
    sha256->used = 0;
332
#endif
333
334
#if (defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
335
     (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))) || \
336
    (defined(WOLFSSL_ARMASM) && defined(__aarch64__) && \
337
     !defined(WOLF_CRYPTO_CB_ONLY_SHA256))
338
    /* choose best Transform function under this runtime environment */
339
    Sha256_SetTransform();
340
#endif
341
342
#ifdef WOLFSSL_MAXQ10XX_CRYPTO
343
    XMEMSET(&sha256->maxq_ctx, 0, sizeof(sha256->maxq_ctx));
344
#endif
345
346
#ifdef HAVE_ARIA
347
    sha256->hSession = NULL;
348
#endif
349
350
237k
    return 0;
351
237k
}
352
353
#if !defined(WOLFSSL_HASH_KEEP) && !defined(WOLF_CRYPTO_CB_ONLY_SHA256)
354
355
/* Reset a hash context to its freshly initialized state, reusing its existing
356
 * allocations.  Like the Final functions, Reset does not destroy sensitive
357
 * internal state; use the matching Free function for teardown at end of life.
358
 *
359
 * The in-place form is only for the software implementation: a CB_ONLY build
360
 * routes hashing through a device whose state InitSha256() cannot restart, so
361
 * it falls back to Free + Init_ex, which gives the callback its teardown and
362
 * re-setup hooks.  (SHA-224's in-place variant sits in the NEED_SOFT arm and
363
 * sha512.c's sit in the software-implementation arm, so both exclude CB_ONLY
364
 * structurally; SHA-256's region also serves the CB_ONLY build -- see
365
 * wc_InitSha224_ex()'s CB_ONLY arm -- hence the explicit conjunct.) */
366
0
int wc_Sha256Reset(wc_Sha256* sha256) {
367
0
    if (sha256 == NULL)
368
0
        return BAD_FUNC_ARG;
369
0
#ifdef WOLF_CRYPTO_CB
370
    /* A device may hang state off devCtx that InitSha256() cannot restart.
371
     * Free and re-init so the callback gets its teardown and setup. */
372
0
    #ifndef WOLF_CRYPTO_CB_FIND
373
0
    if (sha256->devId != INVALID_DEVID)
374
0
    #endif
375
0
    {
376
0
        void* heap = sha256->heap;
377
0
        int devId = sha256->devId;
378
0
        wc_Sha256Free(sha256);
379
0
        return wc_InitSha256_ex(sha256, heap, devId);
380
0
    }
381
0
#endif
382
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256) && \
383
    defined(HAVE_INTEL_QA)
384
    /* QAT caches updates in asyncDev, which InitSha256() cannot discard. */
385
    {
386
        int ret = IntelQaSymHashReset(&sha256->asyncDev);
387
        if (ret != 0)
388
            return ret;
389
    }
390
#endif
391
0
    return InitSha256(sha256);
392
0
}
393
#define WC_SHA256RESET_DEFINED
394
#endif /* !WOLFSSL_HASH_KEEP && !WOLF_CRYPTO_CB_ONLY_SHA256 */
395
396
#endif
397
398
/* Hardware Acceleration */
399
/* Caller-owned transient scratch for the C transform: the message schedule
400
 * and the working variables, so one ForceZero when the public call returns
401
 * wipes all of it at once, instead of per-block wipes inside the transform.
402
 * Natural alignment suffices; only the C transform uses it. */
403
typedef struct Sha256TScratch {
404
#ifdef SHA256_MANY_REGISTERS
405
    /* The MANY_REGISTERS transform rolls a 16-word window. */
406
    word32 W[WC_SHA256_BLOCK_SIZE / sizeof(word32)];
407
#else
408
    word32 W[WC_SHA256_BLOCK_SIZE];
409
#endif
410
    word32 S[8];
411
} Sha256TScratch;
412
413
/* External W providers size by the header constant; keep them in lockstep. */
414
wc_static_assert(sizeof(Sha256TScratch) == WC_SHA256_TSCRATCH_SIZE);
415
416
/* Scratch provisioning for the callers that drive the C transform.  The
417
 * declared pointer is named sha256TScr.  BEGIN validates it (and registers it
418
 * with WOLFSSL_CHECK_MEM_ZERO); WIPE is the single ForceZero (and the
419
 * mem-zero check).  Under WOLFSSL_SMALL_STACK_CACHE the scratch is the
420
 * per-context cache allocated at init and wiped at Free, so BEGIN checks for
421
 * it and WIPE is a no-op, preserving that configuration's zero per-call
422
 * cost. */
423
#if defined(WOLFSSL_SMALL_STACK_CACHE) && !defined(WOLFSSL_NO_MALLOC)
424
    #define WC_SHA256_TSCRATCH_DECL(s) \
425
        Sha256TScratch* sha256TScr = (Sha256TScratch*)(s)->W
426
    #define WC_SHA256_TSCRATCH_BEGIN(s) \
427
        do { if (sha256TScr == NULL) return BAD_FUNC_ARG; } while (0)
428
    #define WC_SHA256_TSCRATCH_WIPE(s) WC_DO_NOTHING /* wiped at Free */
429
#else
430
    /* Stack in big-stack builds, heap under WOLFSSL_SMALL_STACK, per the
431
     * WC_DECLARE_VAR family (one allocation per public call -- the previous
432
     * code allocated and freed per block under WOLFSSL_SMALL_STACK). */
433
    #ifdef WOLFSSL_CHECK_MEM_ZERO
434
        /* Zero first: the registration call takes const void*, and a
435
         * pointer to an uninitialized object trips -Wmaybe-uninitialized
436
         * under -Werror; a deterministic start also suits the checker. */
437
        #define WC_SHA256_TSCRATCH_MZ_ADD()                       \
438
            do {                                                             \
439
                XMEMSET(sha256TScr, 0, sizeof(Sha256TScratch));                   \
440
                wc_MemZero_Add("Sha256 transform scratch", sha256TScr,      \
441
                               sizeof(Sha256TScratch));                       \
442
            } while (0)
443
        #define WC_SHA256_TSCRATCH_MZ_CHECK() \
444
            wc_MemZero_Check(sha256TScr, sizeof(Sha256TScratch))
445
    #else
446
716k
        #define WC_SHA256_TSCRATCH_MZ_ADD() WC_DO_NOTHING
447
716k
        #define WC_SHA256_TSCRATCH_MZ_CHECK() WC_DO_NOTHING
448
    #endif
449
    #define WC_SHA256_TSCRATCH_DECL(s) \
450
716k
        WC_DECLARE_VAR(sha256TScr, Sha256TScratch, 1, (s)->heap)
451
    #define WC_SHA256_TSCRATCH_BEGIN(s)                                      \
452
716k
        do {                                                                 \
453
716k
            WC_ALLOC_VAR_EX(sha256TScr, Sha256TScratch, 1, (s)->heap,        \
454
716k
                            DYNAMIC_TYPE_TMP_BUFFER, return MEMORY_E);       \
455
716k
            WC_SHA256_TSCRATCH_MZ_ADD();                                     \
456
716k
        } while (0)
457
    #define WC_SHA256_TSCRATCH_WIPE(s)                                       \
458
716k
        do {                                                                 \
459
716k
            ForceZero(sha256TScr, sizeof(Sha256TScratch));                   \
460
716k
            WC_SHA256_TSCRATCH_MZ_CHECK();                                   \
461
716k
            WC_FREE_VAR_EX(sha256TScr, (s)->heap, DYNAMIC_TYPE_TMP_BUFFER);  \
462
716k
        } while (0)
463
#endif
464
465
#if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
466
    (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2)) && \
467
    !defined(WOLF_CRYPTO_CB_ONLY_SHA256)
468
469
    /* in case intel instructions aren't available, plus we need the K[] global */
470
    #define NEED_SOFT_SHA256
471
472
    /*****
473
    Intel AVX1/AVX2 Macro Control Structure
474
475
    #define HAVE_INTEL_AVX1
476
    #define HAVE_INTEL_AVX2
477
478
    #define HAVE_INTEL_RORX
479
480
481
    int InitSha256(wc_Sha256* sha256) {
482
         Save/Recover XMM, YMM
483
         ...
484
    }
485
486
    #if defined(HAVE_INTEL_AVX1)|| defined(HAVE_INTEL_AVX2)
487
      Transform_Sha256(); Function prototype
488
    #else
489
      Transform_Sha256() {   }
490
      int Sha256Final() {
491
         Save/Recover XMM, YMM
492
         ...
493
      }
494
    #endif
495
496
    #if defined(HAVE_INTEL_AVX1)|| defined(HAVE_INTEL_AVX2)
497
        #if defined(HAVE_INTEL_RORX
498
             #define RND with rorx instruction
499
        #else
500
            #define RND
501
        #endif
502
    #endif
503
504
    #if defined(HAVE_INTEL_AVX1)
505
506
       #define XMM Instructions/inline asm
507
508
       int Transform_Sha256() {
509
           Stitched Message Sched/Round
510
        }
511
512
    #elif defined(HAVE_INTEL_AVX2)
513
514
      #define YMM Instructions/inline asm
515
516
      int Transform_Sha256() {
517
          More granular Stitched Message Sched/Round
518
      }
519
520
    #endif
521
522
    */
523
524
    /* Each platform needs to query info type 1 from cpuid to see if aesni is
525
     * supported. Also, let's setup a macro for proper linkage w/o ABI conflicts
526
     */
527
528
    /* #if defined(HAVE_INTEL_AVX1/2) at the tail of sha256 */
529
    static int Transform_Sha256(wc_Sha256* sha256, const byte* data);
530
    static int Transform_Sha256_scr(wc_Sha256* sha256, const byte* data,
531
                                    Sha256TScratch* WC_RESTRICT scr);
532
533
#ifdef __cplusplus
534
    extern "C" {
535
#endif
536
537
        extern int Transform_Sha256_SSE2_Sha(wc_Sha256 *sha256,
538
                                             const byte* data);
539
        extern int Transform_Sha256_SSE2_Sha_Len(wc_Sha256* sha256,
540
                                                 const byte* data, word32 len);
541
    #if defined(HAVE_INTEL_AVX1)
542
        extern int Transform_Sha256_AVX1_Sha(wc_Sha256 *sha256,
543
                                             const byte* data);
544
        extern int Transform_Sha256_AVX1_Sha_Len(wc_Sha256* sha256,
545
                                                 const byte* data, word32 len);
546
        extern int Transform_Sha256_AVX1(wc_Sha256 *sha256, const byte* data);
547
        extern int Transform_Sha256_AVX1_Len(wc_Sha256* sha256,
548
                                             const byte* data, word32 len);
549
    #endif
550
    #if defined(HAVE_INTEL_AVX2)
551
        extern int Transform_Sha256_AVX2(wc_Sha256 *sha256, const byte* data);
552
        extern int Transform_Sha256_AVX2_Len(wc_Sha256* sha256,
553
                                             const byte* data, word32 len);
554
        #ifdef HAVE_INTEL_RORX
555
        extern int Transform_Sha256_AVX1_RORX(wc_Sha256 *sha256, const byte* data);
556
        extern int Transform_Sha256_AVX1_RORX_Len(wc_Sha256* sha256,
557
                                                  const byte* data, word32 len);
558
        extern int Transform_Sha256_AVX2_RORX(wc_Sha256 *sha256, const byte* data);
559
        extern int Transform_Sha256_AVX2_RORX_Len(wc_Sha256* sha256,
560
                                                  const byte* data, word32 len);
561
        #endif /* HAVE_INTEL_RORX */
562
    #endif /* HAVE_INTEL_AVX2 */
563
564
#ifdef __cplusplus
565
    }  /* extern "C" */
566
#endif
567
568
    static cpuid_flags_atomic_t intel_flags = WC_CPUID_ATOMIC_INITIALIZER;
569
570
#ifdef WC_NO_INTERNAL_FUNCTION_POINTERS
571
572
    enum sha_methods { SHA256_UNSET = 0, SHA256_AVX1_SHA, SHA256_AVX2,
573
                       SHA256_AVX1_RORX, SHA256_AVX1_NOSHA, SHA256_AVX2_RORX,
574
                       SHA256_SSE2, SHA256_C };
575
576
    /* note that all write access to this static variable must be idempotent,
577
     * as arranged by Sha256_SetTransform(), else it will be susceptible to
578
     * data races.
579
     */
580
    static enum sha_methods sha_method = SHA256_UNSET;
581
582
    static void Sha256_SetTransform(void)
583
    {
584
        if (sha_method != SHA256_UNSET)
585
            return;
586
587
        /* Note, with WC_C_DYNAMIC_FALLBACK, sha_method records CPU capability
588
         * only.  Whether vector registers are actually usable is determined
589
         * independently at each transform via SAVE_VECTOR_REGISTERS2(),
590
         * allowing a context to move freely between vectorized and C transforms
591
         * call by call.
592
         */
593
594
        cpuid_get_flags_atomic(&intel_flags);
595
596
        if (IS_INTEL_SHA(intel_flags)) {
597
        #ifdef HAVE_INTEL_AVX1
598
            if (IS_INTEL_AVX1(intel_flags)) {
599
                sha_method = SHA256_AVX1_SHA;
600
            }
601
            else
602
        #endif
603
            {
604
                sha_method = SHA256_SSE2;
605
            }
606
        }
607
        else
608
    #ifdef HAVE_INTEL_AVX2
609
        if (IS_INTEL_AVX2(intel_flags)) {
610
        #ifdef HAVE_INTEL_RORX
611
            if (IS_INTEL_BMI2(intel_flags)) {
612
                sha_method = SHA256_AVX2_RORX;
613
            }
614
            else
615
        #endif
616
            {
617
                sha_method = SHA256_AVX2;
618
            }
619
        }
620
        else
621
    #endif
622
    #ifdef HAVE_INTEL_AVX1
623
        if (IS_INTEL_AVX1(intel_flags)) {
624
        #ifdef HAVE_INTEL_RORX
625
            if (IS_INTEL_BMI2(intel_flags)) {
626
                sha_method = SHA256_AVX1_RORX;
627
            }
628
            else
629
        #endif
630
            {
631
                sha_method = SHA256_AVX1_NOSHA;
632
            }
633
        }
634
        else
635
    #endif
636
        {
637
            sha_method = SHA256_C;
638
        }
639
    }
640
641
    #ifdef WC_SHA256_RAW_BE_BUFFER
642
643
    static WC_INLINE int Transform_Sha256_C_from_raw_scr(wc_Sha256* S,
644
                                                         const byte* D,
645
                                                         Sha256TScratch* scr)
646
    {
647
        /* D may be unaligned caller data: stage it in the aligned context
648
         * buffer before word-wise byte reversal, and feed the transform
649
         * from there on both endiannesses. */
650
        if (D != (const byte*)S->buffer)
651
            XMEMCPY(S->buffer, D, WC_SHA256_BLOCK_SIZE);
652
    #ifdef LITTLE_ENDIAN_ORDER
653
        ByteReverseWords(S->buffer, S->buffer, WC_SHA256_BLOCK_SIZE);
654
    #endif
655
        return Transform_Sha256_scr(S, (const byte*)S->buffer, scr);
656
    }
657
658
    static WC_INLINE int Transform_Sha256_C_from_raw(wc_Sha256* S,
659
                                                     const byte* D)
660
    {
661
        int ret;
662
        WC_SHA256_TSCRATCH_DECL(S);
663
        WC_SHA256_TSCRATCH_BEGIN(S);
664
        ret = Transform_Sha256_C_from_raw_scr(S, D, sha256TScr);
665
        WC_SHA256_TSCRATCH_WIPE(S);
666
        return ret;
667
    }
668
669
    static WC_INLINE int Transform_Sha256_Len_C_from_raw(wc_Sha256* S,
670
                                                         const byte* D,
671
                                                         word32 L)
672
    {
673
        int ret = 0;
674
        WC_SHA256_TSCRATCH_DECL(S);
675
676
        WC_SHA256_TSCRATCH_BEGIN(S);
677
        while (L >= WC_SHA256_BLOCK_SIZE) {
678
            ret = Transform_Sha256_C_from_raw_scr(S, D, sha256TScr);
679
            if (ret != 0)
680
                break;
681
            D += WC_SHA256_BLOCK_SIZE;
682
            L -= WC_SHA256_BLOCK_SIZE;
683
        }
684
        WC_SHA256_TSCRATCH_WIPE(S);
685
686
        return ret;
687
    }
688
689
    #endif /* WC_SHA256_RAW_BE_BUFFER */
690
691
    static WC_INLINE int inline_XTRANSFORM(wc_Sha256* S, const byte* D) {
692
        int ret;
693
694
    #ifdef WC_C_DYNAMIC_FALLBACK
695
        if ((sha_method == SHA256_C) ||
696
            (SAVE_VECTOR_REGISTERS2() != 0))
697
        {
698
            return Transform_Sha256_C_from_raw(S, D);
699
        }
700
    #else
701
        if (sha_method == SHA256_C) {
702
            #ifdef WC_SHA256_RAW_BE_BUFFER
703
            /* not currently reachable */
704
            return Transform_Sha256_C_from_raw(S, D);
705
            #else
706
            return Transform_Sha256(S, D);
707
            #endif
708
        }
709
        SAVE_VECTOR_REGISTERS(return _svr_ret;);
710
    #endif
711
        switch (sha_method) {
712
        case SHA256_AVX2:
713
            ret = Transform_Sha256_AVX2(S, D);
714
            break;
715
        case SHA256_AVX2_RORX:
716
            ret = Transform_Sha256_AVX2_RORX(S, D);
717
            break;
718
        case SHA256_AVX1_SHA:
719
            ret = Transform_Sha256_AVX1_Sha(S, D);
720
            break;
721
        case SHA256_AVX1_NOSHA:
722
            ret = Transform_Sha256_AVX1(S, D);
723
            break;
724
        case SHA256_AVX1_RORX:
725
            ret = Transform_Sha256_AVX1_RORX(S, D);
726
            break;
727
        case SHA256_SSE2:
728
            ret = Transform_Sha256_SSE2_Sha(S, D);
729
            break;
730
        case SHA256_C:
731
        case SHA256_UNSET:
732
        default:
733
            /* not reachable -- the C path exits above, before vector register
734
             * save -- but must stay layout-correct. */
735
            #ifdef WC_SHA256_RAW_BE_BUFFER
736
            ret = Transform_Sha256_C_from_raw(S, D);
737
            #else
738
            ret = Transform_Sha256(S, D);
739
            #endif
740
            break;
741
        }
742
        RESTORE_VECTOR_REGISTERS();
743
        return ret;
744
    }
745
#define XTRANSFORM(...) inline_XTRANSFORM(__VA_ARGS__)
746
747
    static WC_INLINE int inline_XTRANSFORM_LEN(wc_Sha256* S, const byte* D, word32 L) {
748
        int ret;
749
    #ifdef WC_C_DYNAMIC_FALLBACK
750
        if ((sha_method == SHA256_C) ||
751
            (SAVE_VECTOR_REGISTERS2() != 0))
752
        {
753
            return Transform_Sha256_Len_C_from_raw(S, D, L);
754
        }
755
    #else
756
        SAVE_VECTOR_REGISTERS(return _svr_ret;);
757
    #endif
758
        switch (sha_method) {
759
        case SHA256_AVX2:
760
            ret = Transform_Sha256_AVX2_Len(S, D, L);
761
            break;
762
        case SHA256_AVX2_RORX:
763
            ret = Transform_Sha256_AVX2_RORX_Len(S, D, L);
764
            break;
765
        case SHA256_AVX1_SHA:
766
            ret = Transform_Sha256_AVX1_Sha_Len(S, D, L);
767
            break;
768
        case SHA256_AVX1_NOSHA:
769
            ret = Transform_Sha256_AVX1_Len(S, D, L);
770
            break;
771
        case SHA256_AVX1_RORX:
772
            ret = Transform_Sha256_AVX1_RORX_Len(S, D, L);
773
            break;
774
        case SHA256_SSE2:
775
            ret = Transform_Sha256_SSE2_Sha_Len(S, D, L);
776
            break;
777
        case SHA256_C:
778
        case SHA256_UNSET:
779
        default:
780
            #ifdef WC_SHA256_RAW_BE_BUFFER
781
            ret = Transform_Sha256_Len_C_from_raw(S, D, L);
782
            #else
783
            ret = 0;
784
            #endif
785
            break;
786
        }
787
        RESTORE_VECTOR_REGISTERS();
788
        return ret;
789
    }
790
#define XTRANSFORM_LEN(...) inline_XTRANSFORM_LEN(__VA_ARGS__)
791
792
#else /* !WC_NO_INTERNAL_FUNCTION_POINTERS */
793
794
    static int (*Transform_Sha256_p)(wc_Sha256* sha256, const byte* data);
795
                                                       /* = _Transform_Sha256 */
796
    static int (*Transform_Sha256_Len_p)(wc_Sha256* sha256, const byte* data,
797
                                         word32 len);
798
                                                                    /* = NULL */
799
    static int transform_check = 0;
800
    #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
801
    static int Transform_Sha256_is_vectorized = 0;
802
    #endif
803
804
    static WC_INLINE int inline_XTRANSFORM(wc_Sha256* S, const byte* D) {
805
        int ret;
806
    #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
807
        if (Transform_Sha256_is_vectorized)
808
            SAVE_VECTOR_REGISTERS(return _svr_ret;);
809
    #endif
810
        ret = (*Transform_Sha256_p)(S, D);
811
    #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
812
        if (Transform_Sha256_is_vectorized)
813
            RESTORE_VECTOR_REGISTERS();
814
    #endif
815
        return ret;
816
    }
817
#define XTRANSFORM(...) inline_XTRANSFORM(__VA_ARGS__)
818
819
    static WC_INLINE int inline_XTRANSFORM_LEN(wc_Sha256* S, const byte* D, word32 L) {
820
        int ret;
821
    #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
822
        if (Transform_Sha256_is_vectorized)
823
            SAVE_VECTOR_REGISTERS(return _svr_ret;);
824
    #endif
825
        ret = (*Transform_Sha256_Len_p)(S, D, L);
826
    #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
827
        if (Transform_Sha256_is_vectorized)
828
            RESTORE_VECTOR_REGISTERS();
829
    #endif
830
        return ret;
831
    }
832
#define XTRANSFORM_LEN(...) inline_XTRANSFORM_LEN(__VA_ARGS__)
833
834
    static void Sha256_SetTransform(void)
835
    {
836
837
        if (transform_check)
838
            return;
839
840
        cpuid_get_flags_atomic(&intel_flags);
841
842
        if (IS_INTEL_SHA(intel_flags)) {
843
        #ifdef HAVE_INTEL_AVX1
844
            if (IS_INTEL_AVX1(intel_flags)) {
845
                Transform_Sha256_p = Transform_Sha256_AVX1_Sha;
846
                Transform_Sha256_Len_p = Transform_Sha256_AVX1_Sha_Len;
847
            #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
848
                Transform_Sha256_is_vectorized = 1;
849
            #endif
850
            }
851
            else
852
        #endif
853
            {
854
                Transform_Sha256_p = Transform_Sha256_SSE2_Sha;
855
                Transform_Sha256_Len_p = Transform_Sha256_SSE2_Sha_Len;
856
            #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
857
                Transform_Sha256_is_vectorized = 1;
858
            #endif
859
            }
860
        }
861
        else
862
    #ifdef HAVE_INTEL_AVX2
863
        if (IS_INTEL_AVX2(intel_flags)) {
864
        #ifdef HAVE_INTEL_RORX
865
            if (IS_INTEL_BMI2(intel_flags)) {
866
                Transform_Sha256_p = Transform_Sha256_AVX2_RORX;
867
                Transform_Sha256_Len_p = Transform_Sha256_AVX2_RORX_Len;
868
            #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
869
                Transform_Sha256_is_vectorized = 1;
870
            #endif
871
            }
872
            else
873
        #endif
874
            {
875
                Transform_Sha256_p = Transform_Sha256_AVX2;
876
                Transform_Sha256_Len_p = Transform_Sha256_AVX2_Len;
877
            #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
878
                Transform_Sha256_is_vectorized = 1;
879
            #endif
880
            }
881
        }
882
        else
883
    #endif
884
    #ifdef HAVE_INTEL_AVX1
885
        if (IS_INTEL_AVX1(intel_flags)) {
886
        #ifdef HAVE_INTEL_RORX
887
            if (IS_INTEL_BMI2(intel_flags)) {
888
                Transform_Sha256_p = Transform_Sha256_AVX1_RORX;
889
                Transform_Sha256_Len_p = Transform_Sha256_AVX1_RORX_Len;
890
            #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
891
                Transform_Sha256_is_vectorized = 1;
892
            #endif
893
            }
894
            else
895
        #endif
896
            {
897
                Transform_Sha256_p = Transform_Sha256_AVX1;
898
                Transform_Sha256_Len_p = Transform_Sha256_AVX1_Len;
899
            #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
900
                Transform_Sha256_is_vectorized = 1;
901
            #endif
902
            }
903
        }
904
        else
905
    #endif
906
        {
907
            Transform_Sha256_p = Transform_Sha256;
908
            Transform_Sha256_Len_p = NULL;
909
        #ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
910
            Transform_Sha256_is_vectorized = 0;
911
        #endif
912
        }
913
914
        transform_check = 1;
915
    }
916
917
#endif /* !WC_NO_INTERNAL_FUNCTION_POINTERS */
918
919
#if !defined(WOLFSSL_KCAPI_HASH)
920
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
921
    {
922
        int ret = 0;
923
        if (sha256 == NULL)
924
            return BAD_FUNC_ARG;
925
    #ifdef WC_CTX_IS_ALIGNED
926
        if (!WC_CTX_IS_ALIGNED(sha256, wc_Sha256))
927
            return BAD_ALIGN_E;
928
    #endif
929
930
        WC_SILABS_CLEAR_HASH_CTX(sha256);
931
        sha256->heap = heap;
932
    #ifdef WOLF_CRYPTO_CB
933
        sha256->devId = devId;
934
        sha256->devCtx = NULL;
935
    #endif
936
    #ifdef WOLFSSL_SMALL_STACK_CACHE
937
        sha256->W = (word32*)XMALLOC(sizeof(Sha256TScratch),
938
                                     sha256->heap, DYNAMIC_TYPE_DIGEST);
939
        if (sha256->W == NULL)
940
            return MEMORY_E;
941
    #endif
942
943
        ret = InitSha256(sha256);
944
        if (ret != 0)
945
            return ret;
946
947
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256)
948
        ret = wolfAsync_DevCtxInit(&sha256->asyncDev,
949
                            WOLFSSL_ASYNC_MARKER_SHA256, sha256->heap, devId);
950
    #else
951
        (void)devId;
952
    #endif /* WOLFSSL_ASYNC_CRYPT */
953
954
        return ret;
955
    }
956
#endif /* !WOLFSSL_KCAPI_HASH */
957
958
#elif defined(FREESCALE_LTC_SHA)
959
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
960
    {
961
        (void)heap;
962
        (void)devId;
963
964
        LTC_HASH_Init(LTC_BASE, &sha256->ctx, kLTC_Sha256, NULL, 0);
965
966
        return 0;
967
    }
968
969
#elif defined(FREESCALE_MMCAU_SHA)
970
971
    #ifdef FREESCALE_MMCAU_CLASSIC_SHA
972
        #include "cau_api.h"
973
    #else
974
        #include "fsl_mmcau.h"
975
    #endif
976
977
    #define XTRANSFORM(S, D)         Transform_Sha256(S, D)
978
    #define XTRANSFORM_LEN(S, D, L)  Transform_Sha256_Len(S, D, L)
979
980
    #ifndef WC_HASH_DATA_ALIGNMENT
981
        /* these hardware API's require 4 byte (word32) alignment */
982
        #define WC_HASH_DATA_ALIGNMENT 4
983
    #endif
984
985
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
986
    {
987
        int ret = 0;
988
989
        (void)heap;
990
        (void)devId;
991
992
        ret = wolfSSL_CryptHwMutexLock();
993
        if (ret != 0) {
994
            return ret;
995
        }
996
997
    #ifdef FREESCALE_MMCAU_CLASSIC_SHA
998
        cau_sha256_initialize_output(sha256->digest);
999
    #else
1000
        MMCAU_SHA256_InitializeOutput((uint32_t*)sha256->digest);
1001
    #endif
1002
        wolfSSL_CryptHwMutexUnLock();
1003
1004
        sha256->buffLen = 0;
1005
        sha256->loLen   = 0;
1006
        sha256->hiLen   = 0;
1007
    #ifdef WOLFSSL_SMALL_STACK_CACHE
1008
        sha256->W = NULL;
1009
    #endif
1010
1011
        return ret;
1012
    }
1013
1014
    static int Transform_Sha256(wc_Sha256* sha256, const byte* data)
1015
    {
1016
        int ret = wolfSSL_CryptHwMutexLock();
1017
        if (ret == 0) {
1018
    #ifdef FREESCALE_MMCAU_CLASSIC_SHA
1019
            cau_sha256_hash_n((byte*)data, 1, sha256->digest);
1020
    #else
1021
            MMCAU_SHA256_HashN((byte*)data, 1, (uint32_t*)sha256->digest);
1022
    #endif
1023
            wolfSSL_CryptHwMutexUnLock();
1024
        }
1025
        return ret;
1026
    }
1027
1028
    static int Transform_Sha256_Len(wc_Sha256* sha256, const byte* data,
1029
        word32 len)
1030
    {
1031
        int ret = wolfSSL_CryptHwMutexLock();
1032
        if (ret == 0) {
1033
        #if defined(WC_HASH_DATA_ALIGNMENT) && WC_HASH_DATA_ALIGNMENT > 0
1034
            if ((wc_ptr_t)data % WC_HASH_DATA_ALIGNMENT) {
1035
                /* data pointer is NOT aligned,
1036
                 * so copy and perform one block at a time */
1037
                byte* local = (byte*)sha256->buffer;
1038
                while (len >= WC_SHA256_BLOCK_SIZE) {
1039
                    XMEMCPY(local, data, WC_SHA256_BLOCK_SIZE);
1040
                #ifdef FREESCALE_MMCAU_CLASSIC_SHA
1041
                    cau_sha256_hash_n(local, 1, sha256->digest);
1042
                #else
1043
                    MMCAU_SHA256_HashN(local, 1, (uint32_t*)sha256->digest);
1044
                #endif
1045
                    data += WC_SHA256_BLOCK_SIZE;
1046
                    len  -= WC_SHA256_BLOCK_SIZE;
1047
                }
1048
            }
1049
            else
1050
        #endif
1051
            {
1052
    #ifdef FREESCALE_MMCAU_CLASSIC_SHA
1053
            cau_sha256_hash_n((byte*)data, len/WC_SHA256_BLOCK_SIZE,
1054
                sha256->digest);
1055
    #else
1056
            MMCAU_SHA256_HashN((byte*)data, len/WC_SHA256_BLOCK_SIZE,
1057
                (uint32_t*)sha256->digest);
1058
    #endif
1059
            }
1060
            wolfSSL_CryptHwMutexUnLock();
1061
        }
1062
        return ret;
1063
    }
1064
1065
#elif defined(WOLFSSL_PIC32MZ_HASH)
1066
    #include <wolfssl/wolfcrypt/port/pic32/pic32mz-crypt.h>
1067
1068
#elif defined(STM32_HASH_SHA2)
1069
1070
    /* Supports CubeMX HAL or Standard Peripheral Library */
1071
1072
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1073
    {
1074
        if (sha256 == NULL)
1075
            return BAD_FUNC_ARG;
1076
1077
        WC_SILABS_CLEAR_HASH_CTX(sha256);
1078
        (void)devId;
1079
        (void)heap;
1080
1081
        XMEMSET(sha256, 0, sizeof(wc_Sha256));
1082
        wc_Stm32_Hash_Init(&sha256->stmCtx);
1083
        return 0;
1084
    }
1085
1086
    int wc_Sha256Update(wc_Sha256* sha256, const byte* data, word32 len)
1087
    {
1088
        int ret = 0;
1089
1090
        if (sha256 == NULL) {
1091
            return BAD_FUNC_ARG;
1092
        }
1093
        if (data == NULL && len == 0) {
1094
            /* valid, but do nothing */
1095
            return 0;
1096
        }
1097
        if (data == NULL) {
1098
            return BAD_FUNC_ARG;
1099
        }
1100
1101
        ret = wolfSSL_CryptHwMutexLock();
1102
        if (ret == 0) {
1103
            ret = wc_Stm32_Hash_Update(&sha256->stmCtx,
1104
                HASH_AlgoSelection_SHA256, data, len, WC_SHA256_BLOCK_SIZE);
1105
            wolfSSL_CryptHwMutexUnLock();
1106
        }
1107
        return ret;
1108
    }
1109
1110
    int wc_Sha256Final(wc_Sha256* sha256, byte* hash)
1111
    {
1112
        int ret = 0;
1113
1114
        if (sha256 == NULL || hash == NULL) {
1115
            return BAD_FUNC_ARG;
1116
        }
1117
1118
        ret = wolfSSL_CryptHwMutexLock();
1119
        if (ret == 0) {
1120
            ret = wc_Stm32_Hash_Final(&sha256->stmCtx,
1121
                HASH_AlgoSelection_SHA256, hash, WC_SHA256_DIGEST_SIZE);
1122
            wolfSSL_CryptHwMutexUnLock();
1123
        }
1124
1125
        (void)wc_InitSha256(sha256); /* reset state */
1126
1127
        return ret;
1128
    }
1129
1130
#elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_HASH) && \
1131
    !defined(WOLFSSL_QNX_CAAM)
1132
    /* functions defined in wolfcrypt/src/port/caam/caam_sha256.c */
1133
1134
#elif defined(WOLFSSL_SE050) && defined(WOLFSSL_SE050_HASH)
1135
1136
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1137
    {
1138
        if (sha256 == NULL) {
1139
            return BAD_FUNC_ARG;
1140
        }
1141
    #ifdef WC_CTX_IS_ALIGNED
1142
        if (!WC_CTX_IS_ALIGNED(sha256, wc_Sha256)) {
1143
            return BAD_ALIGN_E;
1144
        }
1145
    #endif
1146
        WC_SILABS_CLEAR_HASH_CTX(sha256);
1147
        (void)devId;
1148
1149
        return se050_hash_init(&sha256->se050Ctx, heap);
1150
    }
1151
1152
    int wc_Sha256Update(wc_Sha256* sha256, const byte* data, word32 len)
1153
    {
1154
        if (sha256 == NULL) {
1155
            return BAD_FUNC_ARG;
1156
        }
1157
        if (data == NULL && len == 0) {
1158
            /* valid, but do nothing */
1159
            return 0;
1160
        }
1161
        if (data == NULL) {
1162
            return BAD_FUNC_ARG;
1163
        }
1164
1165
        return se050_hash_update(&sha256->se050Ctx, data, len);
1166
    }
1167
1168
    int wc_Sha256Final(wc_Sha256* sha256, byte* hash)
1169
    {
1170
        int ret = 0;
1171
        ret = se050_hash_final(&sha256->se050Ctx, hash, WC_SHA256_DIGEST_SIZE,
1172
                               kAlgorithm_SSS_SHA256);
1173
        return ret;
1174
    }
1175
1176
#elif defined(WOLFSSL_AFALG_HASH)
1177
    /* implemented in wolfcrypt/src/port/af_alg/afalg_hash.c */
1178
1179
#elif defined(WOLFSSL_DEVCRYPTO_HASH)
1180
    /* implemented in wolfcrypt/src/port/devcrypto/devcrypt_hash.c */
1181
1182
#elif defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_HASH)
1183
    #include "hal_data.h"
1184
1185
    #ifndef WOLFSSL_SCE_SHA256_HANDLE
1186
        #define WOLFSSL_SCE_SHA256_HANDLE g_sce_hash_0
1187
    #endif
1188
1189
    #define WC_SHA256_DIGEST_WORD_SIZE 16
1190
    #define XTRANSFORM(S, D) wc_Sha256SCE_XTRANSFORM(S, D)
1191
    static int wc_Sha256SCE_XTRANSFORM(wc_Sha256* sha256, const byte* data)
1192
    {
1193
        if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag ==
1194
                CRYPTO_WORD_ENDIAN_LITTLE)
1195
        {
1196
            ByteReverseWords((word32*)data, (word32*)data,
1197
                    WC_SHA256_BLOCK_SIZE);
1198
            ByteReverseWords(sha256->digest, sha256->digest,
1199
                    WC_SHA256_DIGEST_SIZE);
1200
        }
1201
1202
        if (WOLFSSL_SCE_SHA256_HANDLE.p_api->hashUpdate(
1203
                    WOLFSSL_SCE_SHA256_HANDLE.p_ctrl, (word32*)data,
1204
                    WC_SHA256_DIGEST_WORD_SIZE, sha256->digest) != SSP_SUCCESS){
1205
            WOLFSSL_MSG("Unexpected hardware return value");
1206
            return WC_HW_E;
1207
        }
1208
1209
        if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag ==
1210
                CRYPTO_WORD_ENDIAN_LITTLE)
1211
        {
1212
            ByteReverseWords((word32*)data, (word32*)data,
1213
                    WC_SHA256_BLOCK_SIZE);
1214
            ByteReverseWords(sha256->digest, sha256->digest,
1215
                    WC_SHA256_DIGEST_SIZE);
1216
        }
1217
1218
        return 0;
1219
    }
1220
1221
1222
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1223
    {
1224
        int ret = 0;
1225
        if (sha256 == NULL)
1226
            return BAD_FUNC_ARG;
1227
1228
        WC_SILABS_CLEAR_HASH_CTX(sha256);
1229
        sha256->heap = heap;
1230
1231
        ret = InitSha256(sha256);
1232
        if (ret != 0)
1233
            return ret;
1234
1235
        (void)devId;
1236
1237
        return ret;
1238
    }
1239
1240
#elif defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW)
1241
1242
    /* HW may fail since there's only one, so we still need SW */
1243
    #define NEED_SOFT_SHA256
1244
1245
    /*
1246
    ** An Espressif-specific InitSha256()
1247
    **
1248
    ** soft SHA needs initialization digest, but HW does not.
1249
    */
1250
    static int InitSha256(wc_Sha256* sha256)
1251
    {
1252
        int ret = 0; /* zero = success */
1253
1254
        /* We may or may not need initial digest for HW.
1255
         * Always needed for SW-only. */
1256
        sha256->digest[0] = 0x6A09E667L;
1257
        sha256->digest[1] = 0xBB67AE85L;
1258
        sha256->digest[2] = 0x3C6EF372L;
1259
        sha256->digest[3] = 0xA54FF53AL;
1260
        sha256->digest[4] = 0x510E527FL;
1261
        sha256->digest[5] = 0x9B05688CL;
1262
        sha256->digest[6] = 0x1F83D9ABL;
1263
        sha256->digest[7] = 0x5BE0CD19L;
1264
1265
        sha256->buffLen = 0;
1266
        sha256->loLen   = 0;
1267
        sha256->hiLen   = 0;
1268
1269
#ifndef NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256
1270
        ret = esp_sha_init((WC_ESP32SHA*)&(sha256->ctx), WC_HASH_TYPE_SHA256);
1271
#endif
1272
        return ret;
1273
    }
1274
1275
    /*
1276
    ** An Espressif-specific wolfCrypt InitSha256 external wrapper.
1277
    **
1278
    ** we'll assume this is ALWAYS for a new, uninitialized sha256
1279
    */
1280
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1281
    {
1282
        (void)devId;
1283
        if (sha256 == NULL) {
1284
            return BAD_FUNC_ARG;
1285
        }
1286
1287
        WC_SILABS_CLEAR_HASH_CTX(sha256);
1288
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
1289
       !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
1290
        /* We know this is a fresh, uninitialized item, so set to INIT */
1291
        if (sha256->ctx.mode != ESP32_SHA_INIT) {
1292
            ESP_LOGV(TAG, "Set ctx mode from prior value: "
1293
                               "%d", sha256->ctx.mode);
1294
        }
1295
        sha256->ctx.mode = ESP32_SHA_INIT;
1296
    #endif
1297
1298
        return InitSha256(sha256);
1299
    }
1300
1301
#elif (defined(WOLFSSL_RENESAS_TSIP_TLS) || \
1302
       defined(WOLFSSL_RENESAS_TSIP_CRYPTONLY)) && \
1303
    !defined(NO_WOLFSSL_RENESAS_TSIP_CRYPT_HASH)
1304
1305
    /* implemented in wolfcrypt/src/port/Renesas/renesas_tsip_sha.c */
1306
1307
#elif (defined(WOLFSSL_RENESAS_SCEPROTECT) || defined(WOLFSSL_RENESAS_RSIP)) \
1308
     && !defined(NO_WOLFSSL_RENESAS_FSPSM_HASH)
1309
1310
    /* implemented in wolfcrypt/src/port/Renesas/renesas_fspsm_sha.c */
1311
1312
#elif defined(PSOC6_HASH_SHA2)
1313
    /* implemented in wolfcrypt/src/port/cypress/psoc6_crypto.c */
1314
1315
#elif defined(WOLFSSL_IMXRT_DCP)
1316
    #include <wolfssl/wolfcrypt/port/nxp/dcp_port.h>
1317
    /* implemented in wolfcrypt/src/port/nxp/dcp_port.c */
1318
1319
#elif defined(WOLFSSL_NXP_HASHCRYPT_SHA)
1320
    /* implemented in wolfcrypt/src/port/nxp/hashcrypt_port.c */
1321
1322
#elif defined(WOLFSSL_SILABS_SE_ACCEL)
1323
    /* implemented in wolfcrypt/src/port/silabs/silabs_hash.c */
1324
1325
#elif defined(WOLFSSL_KCAPI_HASH)
1326
    /* implemented in wolfcrypt/src/port/kcapi/kcapi_hash.c */
1327
1328
#elif defined(WOLFSSL_HAVE_PSA) && !defined(WOLFSSL_PSA_NO_HASH)
1329
    /* implemented in wolfcrypt/src/port/psa/psa_hash.c */
1330
1331
#elif defined(WOLFSSL_RENESAS_RX64_HASH)
1332
1333
    /* implemented in wolfcrypt/src/port/Renesas/renesas_rx64_hw_sha.c */
1334
#elif (defined(WOLFSSL_PPC32_ASM) || defined(WOLFSSL_PPC64_ASM)) && \
1335
    !defined(WOLF_CRYPTO_CB_ONLY_SHA256)
1336
1337
extern void Transform_Sha256_Len(wc_Sha256* sha256, const byte* data,
1338
    word32 len);
1339
1340
#if defined(WOLFSSL_PPC64_ASM) && defined(WOLFSSL_PPC64_ASM_CRYPTO)
1341
/* POWER8+ has a vector SHA-256 sigma instruction (vshasigmaw).  When built
1342
 * in, select that implementation at run time if the CPU supports it.
1343
 *
1344
 * A run-time flag with direct calls is used rather than a function pointer:
1345
 * an indirect call would require an ELFv1 function descriptor, whereas direct
1346
 * calls work under both the ELFv1 and ELFv2 ABIs. */
1347
extern void Transform_Sha256_Len_crypto(wc_Sha256* sha256, const byte* data,
1348
    word32 len);
1349
1350
/* -1 = not yet determined, 0 = base, 1 = vector-crypto */
1351
/* Resolved dispatch decision (0 = base, 1 = vector-crypto), accessed with the
1352
 * wolfSSL atomic APIs so the one-time detection is free of data races.  The
1353
 * write is idempotent (all callers compute the same value from the atomic
1354
 * master flags), so a benign concurrent double-write is harmless. */
1355
static wolfSSL_Atomic_Uint sha256_use_crypto = WOLFSSL_ATOMIC_INITIALIZER(0);
1356
1357
/* Detect CPU support via the central cpuid module. */
1358
static void Sha256_SetTransform(void)
1359
{
1360
    WOLFSSL_ATOMIC_STORE(sha256_use_crypto,
1361
        (unsigned int)(IS_PPC64_VEC_CRYPTO(cpuid_get_flags()) != 0));
1362
}
1363
1364
static WC_INLINE int SHA256_TRANSFORM_LEN(wc_Sha256* sha256, const byte* data,
1365
    word32 len)
1366
{
1367
    if (WOLFSSL_ATOMIC_LOAD(sha256_use_crypto))
1368
        Transform_Sha256_Len_crypto(sha256, data, len);
1369
    else
1370
        Transform_Sha256_Len(sha256, data, len);
1371
    return 0;
1372
}
1373
#else
1374
#define Sha256_SetTransform()           WC_DO_NOTHING
1375
static WC_INLINE int SHA256_TRANSFORM_LEN(wc_Sha256* sha256, const byte* data,
1376
    word32 len)
1377
{
1378
    Transform_Sha256_Len(sha256, data, len);
1379
    return 0;
1380
}
1381
#endif
1382
1383
int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1384
{
1385
    int ret = 0;
1386
1387
    if (sha256 == NULL)
1388
        return BAD_FUNC_ARG;
1389
    WC_SILABS_CLEAR_HASH_CTX(sha256);
1390
    ret = InitSha256(sha256);
1391
    if (ret != 0)
1392
        return ret;
1393
1394
    Sha256_SetTransform();
1395
1396
    sha256->heap = heap;
1397
#ifdef WOLF_CRYPTO_CB
1398
    sha256->devId = devId;
1399
    sha256->devCtx = NULL;
1400
#else
1401
    (void)devId;
1402
#endif
1403
1404
#ifdef WOLFSSL_SMALL_STACK_CACHE
1405
    sha256->W = NULL;
1406
#endif
1407
1408
    return ret;
1409
}
1410
1411
static int Transform_Sha256(wc_Sha256* sha256, const byte* data)
1412
{
1413
    SHA256_TRANSFORM_LEN(sha256, data, WC_SHA256_BLOCK_SIZE);
1414
    return 0;
1415
}
1416
1417
#define XTRANSFORM Transform_Sha256
1418
#define XTRANSFORM_LEN(s, d, l)         SHA256_TRANSFORM_LEN(s, d, l)
1419
1420
#elif defined(WOLFSSL_ARMASM) && defined(__aarch64__) && \
1421
      !defined(WOLF_CRYPTO_CB_ONLY_SHA256)
1422
1423
/* This arm of the chain provides Sha256_SetTransform() - marks it available to
1424
 * the SHA-224 initializer, which shares the SHA-256 transform.  Earlier arms
1425
 * (hardware hash ports) win the chain and provide no such selection. */
1426
#define WOLFSSL_ARMASM_SHA256_TRANSFORM
1427
1428
static int transform_check = 0;
1429
static cpuid_flags_atomic_t cpuid_flags = WC_CPUID_ATOMIC_INITIALIZER;
1430
1431
static int Transform_Sha256(wc_Sha256* sha256, const byte* data);
1432
static int Transform_Sha256_scr(wc_Sha256* sha256, const byte* data,
1433
                                Sha256TScratch* WC_RESTRICT scr);
1434
static int Transform_Sha256_Len(wc_Sha256* sha256, const byte* data,
1435
     word32 len);
1436
1437
/* Initialize to the software fallback so the pointer is never NULL if it is
1438
 * read before Sha256_SetTransform() has published the selected variant. */
1439
static int (*Transform_Sha256_Len_p)(wc_Sha256* sha256, const byte* data,
1440
     word32 len) = Transform_Sha256_Len;
1441
1442
static WC_INLINE int Transform_Sha256_aarch64(wc_Sha256* sha256,
1443
     const byte* data)
1444
{
1445
    return (*Transform_Sha256_Len_p)(sha256, data, WC_SHA256_BLOCK_SIZE);
1446
}
1447
1448
static WC_INLINE int Transform_Sha256_Len_aarch64(wc_Sha256* sha256,
1449
    const byte* data, word32 len)
1450
{
1451
    return (*Transform_Sha256_Len_p)(sha256, data, len);
1452
}
1453
1454
/* Both transforms below run on v0-v31 and save d8-d15
1455
 * (port/arm/armv8-sha256-asm.S), so a kernel module must bracket them. */
1456
#if defined(__aarch64__) && defined(WOLFSSL_USE_SAVE_VECTOR_REGISTERS)
1457
    #define WC_SHA256_ARM64_SVR_BEGIN()                                     \
1458
        do { int _svr_ret = SAVE_VECTOR_REGISTERS2();                       \
1459
             if (_svr_ret != 0) return _svr_ret; } while (0)
1460
    #define WC_SHA256_ARM64_SVR_END()  RESTORE_VECTOR_REGISTERS()
1461
#else
1462
    #define WC_SHA256_ARM64_SVR_BEGIN() WC_DO_NOTHING
1463
    #define WC_SHA256_ARM64_SVR_END()   WC_DO_NOTHING
1464
#endif
1465
1466
#if !defined(WOLFSSL_ARMASM_NO_NEON)
1467
#if !defined(WOLFSSL_ARMASM_NO_HW_CRYPTO)
1468
static int Transform_Sha256_Len_crypto_aarch64(wc_Sha256* sha256,
1469
    const byte* data, word32 len)
1470
{
1471
    WC_SHA256_ARM64_SVR_BEGIN();
1472
    Transform_Sha256_Len_crypto(sha256, data, len);
1473
    WC_SHA256_ARM64_SVR_END();
1474
    return 0;
1475
}
1476
#endif
1477
1478
static int Transform_Sha256_Len_neon_aarch64(wc_Sha256* sha256,
1479
    const byte* data, word32 len)
1480
{
1481
    WC_SHA256_ARM64_SVR_BEGIN();
1482
    Transform_Sha256_Len_neon(sha256, data, len);
1483
    WC_SHA256_ARM64_SVR_END();
1484
    return 0;
1485
}
1486
#endif
1487
1488
static int Transform_Sha256_Len(wc_Sha256* sha256, const byte* data,
1489
    word32 len)
1490
{
1491
    int ret = 0;
1492
    word32 buffer[WC_SHA256_BLOCK_SIZE / sizeof(word32)];
1493
    WC_SHA256_TSCRATCH_DECL(sha256);
1494
1495
    WC_SHA256_TSCRATCH_BEGIN(sha256);
1496
#ifdef WOLFSSL_CHECK_MEM_ZERO
1497
    wc_MemZero_Add("Transform_Sha256_Len buffer", buffer, sizeof(buffer));
1498
#endif
1499
    while (len >= WC_SHA256_BLOCK_SIZE) {
1500
        XMEMCPY(buffer, data, WC_SHA256_BLOCK_SIZE);
1501
    #ifdef LITTLE_ENDIAN_ORDER
1502
        ByteReverseWords(buffer, buffer, WC_SHA256_BLOCK_SIZE);
1503
    #endif
1504
        ret = Transform_Sha256_scr(sha256, (const byte*)buffer, sha256TScr);
1505
        if (ret != 0)
1506
            break;
1507
        data += WC_SHA256_BLOCK_SIZE;
1508
        len  -= WC_SHA256_BLOCK_SIZE;
1509
    }
1510
    WC_SHA256_TSCRATCH_WIPE(sha256);
1511
    ForceZero(buffer, sizeof(buffer));
1512
#ifdef WOLFSSL_CHECK_MEM_ZERO
1513
    wc_MemZero_Check(buffer, sizeof(buffer));
1514
#endif
1515
1516
    return ret;
1517
}
1518
1519
static void Sha256_SetTransform(void)
1520
{
1521
    if (transform_check)
1522
        return;
1523
1524
    cpuid_get_flags_atomic(&cpuid_flags);
1525
1526
#if !defined(WOLFSSL_ARMASM_NO_NEON)
1527
#if !defined(WOLFSSL_ARMASM_NO_HW_CRYPTO)
1528
    if (IS_AARCH64_SHA256(cpuid_flags)) {
1529
        Transform_Sha256_Len_p = Transform_Sha256_Len_crypto_aarch64;
1530
    }
1531
    else
1532
#endif
1533
    if (IS_AARCH64_ASIMD(cpuid_flags)) {
1534
        Transform_Sha256_Len_p = Transform_Sha256_Len_neon_aarch64;
1535
    }
1536
    else
1537
#endif
1538
    {
1539
        Transform_Sha256_Len_p = Transform_Sha256_Len;
1540
    }
1541
1542
    transform_check = 1;
1543
}
1544
1545
#define XTRANSFORM      Transform_Sha256_aarch64
1546
#define XTRANSFORM_LEN  Transform_Sha256_Len_aarch64
1547
1548
int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1549
{
1550
    int ret = 0;
1551
1552
    if (sha256 == NULL)
1553
        return BAD_FUNC_ARG;
1554
    WC_SILABS_CLEAR_HASH_CTX(sha256);
1555
    ret = InitSha256(sha256);
1556
    if (ret != 0)
1557
        return ret;
1558
1559
    sha256->heap = heap;
1560
#ifdef WOLF_CRYPTO_CB
1561
    sha256->devId = devId;
1562
    sha256->devCtx = NULL;
1563
#else
1564
    (void)devId;
1565
#endif
1566
1567
#ifdef WOLFSSL_SMALL_STACK_CACHE
1568
    sha256->W = (word32*)XMALLOC(sizeof(Sha256TScratch),
1569
                                 sha256->heap, DYNAMIC_TYPE_DIGEST);
1570
    if (sha256->W == NULL)
1571
        return MEMORY_E;
1572
#endif
1573
1574
    return ret;
1575
}
1576
1577
#define NEED_SOFT_SHA256
1578
1579
#elif defined(WOLFSSL_ARMASM) && !defined(WOLF_CRYPTO_CB_ONLY_SHA256)
1580
1581
/* As in the AArch64 arm above: this arm provides Sha256_SetTransform(). */
1582
#define WOLFSSL_ARMASM_SHA256_TRANSFORM
1583
1584
/* On 32-bit Arm a NEON build compiles in the base and NEON and (unless
1585
 * disabled) the Armv8 crypto-extension block transforms, so the best supported
1586
 * one is chosen at run time - mirroring the AArch64 path.  Thumb-2, no-NEON,
1587
 * no-crypto (NO_HW_CRYPTO) and crypto-only (NO_NEON_IMPL) builds compile a
1588
 * single variant and call it directly, as does a build with no run-time
1589
 * detection to dispatch on (HAVE_CPUID_ARM32). */
1590
#if !defined(WOLFSSL_ARMASM_THUMB2) && !defined(WOLFSSL_ARMASM_NO_NEON) && \
1591
    !defined(WOLFSSL_ARMASM_NO_HW_CRYPTO) && \
1592
    !(defined(WOLFSSL_ARMASM_NO_NEON_IMPL) && \
1593
      defined(WOLFSSL_ARMASM_NO_BASE_IMPL)) && defined(HAVE_CPUID_ARM32)
1594
    #define SHA256_ARM32_DISPATCH
1595
#endif
1596
1597
/* The crypto and NEON transforms run on the q registers, so a kernel module
1598
 * must hold the vector registers around them; the base transform needs none. */
1599
#if !defined(WOLFSSL_ARMASM_THUMB2) && !defined(WOLFSSL_ARMASM_NO_NEON)
1600
#ifdef WOLFSSL_USE_SAVE_VECTOR_REGISTERS
1601
    #define WC_SHA256_ARM32_SVR_BEGIN()                                     \
1602
        do { int _svr_ret = SAVE_VECTOR_REGISTERS2();                       \
1603
             if (_svr_ret != 0) return _svr_ret; } while (0)
1604
    #define WC_SHA256_ARM32_SVR_END()  RESTORE_VECTOR_REGISTERS()
1605
#else
1606
    #define WC_SHA256_ARM32_SVR_BEGIN() WC_DO_NOTHING
1607
    #define WC_SHA256_ARM32_SVR_END()   WC_DO_NOTHING
1608
#endif
1609
#ifndef WOLFSSL_ARMASM_NO_HW_CRYPTO
1610
static WC_INLINE int Transform_Sha256_Len_crypto_arm32(wc_Sha256* sha256,
1611
    const byte* data, word32 len)
1612
{
1613
    WC_SHA256_ARM32_SVR_BEGIN();
1614
    Transform_Sha256_Len_crypto(sha256, data, len);
1615
    WC_SHA256_ARM32_SVR_END();
1616
    return 0;
1617
}
1618
#endif
1619
/* Guarded exactly as armv8-32-sha256-asm_c.c guards the assembly it calls, so
1620
 * a wrapper exists only where its implementation does. */
1621
#if !defined(WOLFSSL_ARMASM_NO_NEON_IMPL) || defined(WOLFSSL_ARMASM_NO_HW_CRYPTO)
1622
static WC_INLINE int Transform_Sha256_Len_neon_arm32(wc_Sha256* sha256,
1623
    const byte* data, word32 len)
1624
{
1625
    WC_SHA256_ARM32_SVR_BEGIN();
1626
    Transform_Sha256_Len_neon(sha256, data, len);
1627
    WC_SHA256_ARM32_SVR_END();
1628
    return 0;
1629
}
1630
#endif
1631
#endif
1632
#if !defined(WOLFSSL_ARMASM_NO_BASE_IMPL) || defined(WOLFSSL_ARMASM_NO_NEON)
1633
static WC_INLINE int Transform_Sha256_Len_base_arm32(wc_Sha256* sha256,
1634
    const byte* data, word32 len)
1635
{
1636
    Transform_Sha256_Len_base(sha256, data, len);
1637
    return 0;
1638
}
1639
#endif
1640
1641
#ifdef SHA256_ARM32_DISPATCH
1642
1643
static int sha256_transform_check = 0;
1644
static cpuid_flags_atomic_t sha256_cpuid_flags = WC_CPUID_ATOMIC_INITIALIZER;
1645
1646
/* Initialize to the transform that needs the least of the CPU - the base one
1647
 * requires no extension at all - so the pointer is safe to use even if read
1648
 * before Sha256_SetTransform() runs. */
1649
#ifndef WOLFSSL_ARMASM_NO_BASE_IMPL
1650
    #define SHA256_ARM32_TRANSFORM_INIT     Transform_Sha256_Len_base_arm32
1651
#else
1652
    #define SHA256_ARM32_TRANSFORM_INIT     Transform_Sha256_Len_neon_arm32
1653
#endif
1654
1655
static int (*Transform_Sha256_Len_p)(wc_Sha256* sha256, const byte* data,
1656
    word32 len) = SHA256_ARM32_TRANSFORM_INIT;
1657
1658
/* Select the crypto-extension transform when the CPU implements FEAT_SHA256,
1659
 * otherwise the best fallback this build kept: NEON when the CPU implements
1660
 * Advanced SIMD, else the base transform.  Either fallback can be dropped
1661
 * (WOLFSSL_ARMASM_NO_NEON_IMPL / WOLFSSL_ARMASM_NO_BASE_IMPL) - dropping both
1662
 * is what turns dispatch off above. */
1663
static void Sha256_SetTransform(void)
1664
{
1665
    if (sha256_transform_check)
1666
        return;
1667
1668
    cpuid_get_flags_atomic(&sha256_cpuid_flags);
1669
1670
    if (IS_ARM32_SHA256(sha256_cpuid_flags)) {
1671
        Transform_Sha256_Len_p = Transform_Sha256_Len_crypto_arm32;
1672
    }
1673
#if !defined(WOLFSSL_ARMASM_NO_NEON_IMPL) && \
1674
    !defined(WOLFSSL_ARMASM_NO_BASE_IMPL)
1675
    else if (IS_ARM32_ASIMD(sha256_cpuid_flags)) {
1676
        Transform_Sha256_Len_p = Transform_Sha256_Len_neon_arm32;
1677
    }
1678
    else {
1679
        Transform_Sha256_Len_p = Transform_Sha256_Len_base_arm32;
1680
    }
1681
#elif !defined(WOLFSSL_ARMASM_NO_NEON_IMPL)
1682
    /* Base dropped - a NEON build always implements Advanced SIMD. */
1683
    else {
1684
        Transform_Sha256_Len_p = Transform_Sha256_Len_neon_arm32;
1685
    }
1686
#else
1687
    /* NEON implementation dropped - the base transform needs no extension. */
1688
    else {
1689
        Transform_Sha256_Len_p = Transform_Sha256_Len_base_arm32;
1690
    }
1691
#endif
1692
1693
    sha256_transform_check = 1;
1694
}
1695
1696
#else
1697
#define Sha256_SetTransform()   WC_DO_NOTHING
1698
#endif /* SHA256_ARM32_DISPATCH */
1699
1700
int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1701
{
1702
    int ret = 0;
1703
1704
    if (sha256 == NULL)
1705
        return BAD_FUNC_ARG;
1706
    WC_SILABS_CLEAR_HASH_CTX(sha256);
1707
    ret = InitSha256(sha256);
1708
    if (ret != 0)
1709
        return ret;
1710
1711
    Sha256_SetTransform();
1712
1713
    sha256->heap = heap;
1714
#ifdef WOLF_CRYPTO_CB
1715
    sha256->devId = devId;
1716
    sha256->devCtx = NULL;
1717
#else
1718
    (void)devId;
1719
#endif
1720
1721
    #ifdef WOLFSSL_SMALL_STACK_CACHE
1722
    sha256->W = NULL;
1723
    #endif
1724
1725
    return ret;
1726
}
1727
1728
/* Call the transform selected at run time, or - when only one variant is
1729
 * compiled in - the single one this build has.  The base transform is the
1730
 * choice for Thumb-2 and no-NEON builds, NEON when the crypto extension is off,
1731
 * and otherwise the crypto-extension transform the build was configured for. */
1732
static WC_INLINE int Transform_Sha256(wc_Sha256* sha256, const byte* data)
1733
{
1734
#ifdef SHA256_ARM32_DISPATCH
1735
    return (*Transform_Sha256_Len_p)(sha256, data, WC_SHA256_BLOCK_SIZE);
1736
#elif defined(WOLFSSL_ARMASM_THUMB2) || defined(WOLFSSL_ARMASM_NO_NEON)
1737
    return Transform_Sha256_Len_base_arm32(sha256, data, WC_SHA256_BLOCK_SIZE);
1738
#elif defined(WOLFSSL_ARMASM_NO_HW_CRYPTO)
1739
    return Transform_Sha256_Len_neon_arm32(sha256, data, WC_SHA256_BLOCK_SIZE);
1740
#else
1741
    return Transform_Sha256_Len_crypto_arm32(sha256, data,
1742
        WC_SHA256_BLOCK_SIZE);
1743
#endif
1744
}
1745
1746
/* Multi-block form of Transform_Sha256() - see there for the selection. */
1747
static WC_INLINE int Transform_Sha256_Len(wc_Sha256* sha256, const byte* data,
1748
    word32 len)
1749
{
1750
#ifdef SHA256_ARM32_DISPATCH
1751
    return (*Transform_Sha256_Len_p)(sha256, data, len);
1752
#elif defined(WOLFSSL_ARMASM_THUMB2) || defined(WOLFSSL_ARMASM_NO_NEON)
1753
    return Transform_Sha256_Len_base_arm32(sha256, data, len);
1754
#elif defined(WOLFSSL_ARMASM_NO_HW_CRYPTO)
1755
    return Transform_Sha256_Len_neon_arm32(sha256, data, len);
1756
#else
1757
    return Transform_Sha256_Len_crypto_arm32(sha256, data, len);
1758
#endif
1759
}
1760
1761
#define XTRANSFORM      Transform_Sha256
1762
#define XTRANSFORM_LEN  Transform_Sha256_Len
1763
1764
#elif defined(WOLFSSL_RISCV_ASM) && !defined(WOLF_CRYPTO_CB_ONLY_SHA256)
1765
1766
int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1767
{
1768
    int ret = 0;
1769
1770
    if (sha256 == NULL)
1771
        return BAD_FUNC_ARG;
1772
    WC_SILABS_CLEAR_HASH_CTX(sha256);
1773
    ret = InitSha256(sha256);
1774
    if (ret != 0)
1775
        return ret;
1776
1777
    sha256->heap = heap;
1778
#ifdef WOLF_CRYPTO_CB
1779
    sha256->devId = devId;
1780
    sha256->devCtx = NULL;
1781
#else
1782
    (void)devId;
1783
#endif
1784
1785
#ifdef WOLFSSL_SMALL_STACK_CACHE
1786
    sha256->W = NULL;
1787
#endif
1788
1789
    return ret;
1790
}
1791
1792
static WC_INLINE int Transform_Sha256(wc_Sha256* sha256, const byte* data)
1793
{
1794
#if defined(WOLFSSL_RISCV_VECTOR_CRYPTO_ASM)
1795
    Transform_Sha256_Len_riscv_vector(sha256, data, WC_SHA256_BLOCK_SIZE);
1796
#elif defined(WOLFSSL_RISCV_SCALAR_CRYPTO_ASM)
1797
    Transform_Sha256_Len_riscv_crypto(sha256, data, WC_SHA256_BLOCK_SIZE);
1798
#else
1799
    Transform_Sha256_Len_riscv(sha256, data, WC_SHA256_BLOCK_SIZE);
1800
#endif
1801
    return 0;
1802
}
1803
1804
static WC_INLINE int Transform_Sha256_Len(wc_Sha256* sha256, const byte* data,
1805
    word32 len)
1806
{
1807
#if defined(WOLFSSL_RISCV_VECTOR_CRYPTO_ASM)
1808
    Transform_Sha256_Len_riscv_vector(sha256, data, len);
1809
#elif defined(WOLFSSL_RISCV_SCALAR_CRYPTO_ASM)
1810
    Transform_Sha256_Len_riscv_crypto(sha256, data, len);
1811
#else
1812
    Transform_Sha256_Len_riscv(sha256, data, len);
1813
#endif
1814
    return 0;
1815
}
1816
#define XTRANSFORM      Transform_Sha256
1817
#define XTRANSFORM_LEN  Transform_Sha256_Len
1818
1819
#elif defined(WOLF_CRYPTO_CB_ONLY_SHA256)
1820
    /* Software SHA-256 stripped; every op dispatches via cryptocb. */
1821
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1822
    {
1823
        int ret;
1824
        if (sha256 == NULL)
1825
            return BAD_FUNC_ARG;
1826
    #ifdef WC_CTX_IS_ALIGNED
1827
        if (!WC_CTX_IS_ALIGNED(sha256, wc_Sha256))
1828
            return BAD_ALIGN_E;
1829
    #endif
1830
        WC_SILABS_CLEAR_HASH_CTX(sha256);
1831
        ret = InitSha256(sha256);
1832
        if (ret != 0)
1833
            return ret;
1834
        sha256->heap   = heap;
1835
        sha256->devId  = devId;
1836
        sha256->devCtx = NULL;
1837
        return ret;
1838
    }
1839
#else
1840
    #define NEED_SOFT_SHA256
1841
1842
    int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId)
1843
127k
    {
1844
127k
        int ret = 0;
1845
127k
        if (sha256 == NULL)
1846
0
            return BAD_FUNC_ARG;
1847
127k
    #ifdef WC_CTX_IS_ALIGNED
1848
127k
        if (!WC_CTX_IS_ALIGNED(sha256, wc_Sha256))
1849
0
            return BAD_ALIGN_E;
1850
127k
    #endif
1851
127k
        WC_SILABS_CLEAR_HASH_CTX(sha256);
1852
127k
        ret = InitSha256(sha256);
1853
127k
        if (ret != 0)
1854
0
            return ret;
1855
1856
127k
        sha256->heap = heap;
1857
127k
    #ifdef WOLF_CRYPTO_CB
1858
127k
        sha256->devId = devId;
1859
127k
        sha256->devCtx = NULL;
1860
127k
    #endif
1861
    #ifdef WOLFSSL_SMALL_STACK_CACHE
1862
        sha256->W = (word32*)XMALLOC(sizeof(Sha256TScratch),
1863
                                     sha256->heap, DYNAMIC_TYPE_DIGEST);
1864
        if (sha256->W == NULL)
1865
            return MEMORY_E;
1866
    #endif
1867
1868
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256)
1869
        ret = wolfAsync_DevCtxInit(&sha256->asyncDev,
1870
                            WOLFSSL_ASYNC_MARKER_SHA256, sha256->heap, devId);
1871
    #else
1872
127k
        (void)devId;
1873
127k
    #endif /* WOLFSSL_ASYNC_CRYPT */
1874
    #ifdef WOLFSSL_IMXRT1170_CAAM
1875
         ret = wc_CAAM_HashInit(&sha256->hndl, &sha256->ctx, WC_HASH_TYPE_SHA256);
1876
    #endif
1877
1878
127k
        return ret;
1879
127k
    }
1880
#endif /* End Hardware Acceleration */
1881
1882
#ifdef NEED_SOFT_SHA256
1883
1884
    static const FLASH_QUALIFIER ALIGN32 word32 K[64] = {
1885
        0x428A2F98L, 0x71374491L, 0xB5C0FBCFL, 0xE9B5DBA5L, 0x3956C25BL,
1886
        0x59F111F1L, 0x923F82A4L, 0xAB1C5ED5L, 0xD807AA98L, 0x12835B01L,
1887
        0x243185BEL, 0x550C7DC3L, 0x72BE5D74L, 0x80DEB1FEL, 0x9BDC06A7L,
1888
        0xC19BF174L, 0xE49B69C1L, 0xEFBE4786L, 0x0FC19DC6L, 0x240CA1CCL,
1889
        0x2DE92C6FL, 0x4A7484AAL, 0x5CB0A9DCL, 0x76F988DAL, 0x983E5152L,
1890
        0xA831C66DL, 0xB00327C8L, 0xBF597FC7L, 0xC6E00BF3L, 0xD5A79147L,
1891
        0x06CA6351L, 0x14292967L, 0x27B70A85L, 0x2E1B2138L, 0x4D2C6DFCL,
1892
        0x53380D13L, 0x650A7354L, 0x766A0ABBL, 0x81C2C92EL, 0x92722C85L,
1893
        0xA2BFE8A1L, 0xA81A664BL, 0xC24B8B70L, 0xC76C51A3L, 0xD192E819L,
1894
        0xD6990624L, 0xF40E3585L, 0x106AA070L, 0x19A4C116L, 0x1E376C08L,
1895
        0x2748774CL, 0x34B0BCB5L, 0x391C0CB3L, 0x4ED8AA4AL, 0x5B9CCA4FL,
1896
        0x682E6FF3L, 0x748F82EEL, 0x78A5636FL, 0x84C87814L, 0x8CC70208L,
1897
        0x90BEFFFAL, 0xA4506CEBL, 0xBEF9A3F7L, 0xC67178F2L
1898
    };
1899
1900
/* Both versions of Ch and Maj are logically the same, but with the second set
1901
    the compilers can recognize them better for optimization */
1902
#ifdef WOLFSSL_SHA256_BY_SPEC
1903
    /* SHA256 math based on specification */
1904
50.0M
    #define Ch(x,y,z)       ((z) ^ ((x) & ((y) ^ (z))))
1905
50.0M
    #define Maj(x,y,z)      ((((x) | (y)) & (z)) | ((x) & (y)))
1906
#else
1907
    /* SHA256 math reworked for easier compiler optimization */
1908
    #define Ch(x,y,z)       ((((y) ^ (z)) & (x)) ^ (z))
1909
    #define Maj(x,y,z)      ((((x) ^ (y)) & ((y) ^ (z))) ^ (y))
1910
#endif
1911
75.0M
    #define R(x, n)         (((x) & 0xFFFFFFFFU) >> (n))
1912
1913
450M
    #define S(x, n)         rotrFixed(x, n)
1914
50.0M
    #define Sigma0(x)       (S(x, 2)  ^ S(x, 13) ^ S(x, 22))
1915
50.0M
    #define Sigma1(x)       (S(x, 6)  ^ S(x, 11) ^ S(x, 25))
1916
37.5M
    #define Gamma0(x)       (S(x, 7)  ^ S(x, 18) ^ R(x, 3))
1917
37.5M
    #define Gamma1(x)       (S(x, 17) ^ S(x, 19) ^ R(x, 10))
1918
1919
    #define a(i) S[(0-(i)) & 7]
1920
    #define b(i) S[(1-(i)) & 7]
1921
    #define c(i) S[(2-(i)) & 7]
1922
50.0M
    #define d(i) S[(3-(i)) & 7]
1923
    #define e(i) S[(4-(i)) & 7]
1924
    #define f(i) S[(5-(i)) & 7]
1925
    #define g(i) S[(6-(i)) & 7]
1926
100M
    #define h(i) S[(7-(i)) & 7]
1927
1928
    #ifndef XTRANSFORM
1929
782k
         #define XTRANSFORM(S, D)         Transform_Sha256(S, D)
1930
    #endif
1931
1932
#ifndef SHA256_MANY_REGISTERS
1933
    #define RND(j) \
1934
50.0M
         t0 = h(j) + Sigma1(e(j)) + Ch(e(j), f(j), g(j)) + K[i+(j)] + W[i+(j)]; \
1935
50.0M
         t1 = Sigma0(a(j)) + Maj(a(j), b(j), c(j)); \
1936
50.0M
         d(j) += t0; \
1937
50.0M
         h(j)  = t0 + t1
1938
1939
    static int Transform_Sha256_scr(wc_Sha256* sha256, const byte* data,
1940
                                    Sha256TScratch* WC_RESTRICT scr)
1941
782k
    {
1942
782k
        word32 t0, t1;
1943
782k
        int i;
1944
782k
        word32* WC_RESTRICT W = scr->W;
1945
782k
        word32* WC_RESTRICT S = scr->S;
1946
1947
        /* Copy context->state[] to working vars */
1948
7.03M
        for (i = 0; i < 8; i++)
1949
6.25M
            S[i] = sha256->digest[i];
1950
1951
13.2M
        for (i = 0; i < 16; i++) {
1952
#ifdef WOLFSSL_WIDE_BYTE
1953
            W[i] = *((const word32*)&data[i*(int)sizeof(word32)]);
1954
#else
1955
12.5M
            W[i] = readUnalignedWord32(&data[i*(int)sizeof(word32)]);
1956
12.5M
#endif
1957
12.5M
        }
1958
1959
38.3M
        for (i = 16; i < WC_SHA256_BLOCK_SIZE; i++)
1960
37.5M
            W[i] = Gamma1(W[i-2]) + W[i-7] + Gamma0(W[i-15]) + W[i-16];
1961
1962
    #ifdef USE_SLOW_SHA256
1963
        /* not unrolled - ~2k smaller and ~25% slower */
1964
        for (i = 0; i < WC_SHA256_BLOCK_SIZE; i += 8) {
1965
            int j;
1966
            for (j = 0; j < 8; j++) { /* braces needed here for macros {} */
1967
                RND(j);
1968
            }
1969
        }
1970
    #else
1971
        /* partially loop unrolled */
1972
7.03M
        for (i = 0; i < WC_SHA256_BLOCK_SIZE; i += 8) {
1973
6.25M
            RND(0); RND(1); RND(2); RND(3);
1974
6.25M
            RND(4); RND(5); RND(6); RND(7);
1975
6.25M
        }
1976
782k
    #endif /* USE_SLOW_SHA256 */
1977
1978
        /* Add the working vars back into digest state[] */
1979
7.03M
        for (i = 0; i < 8; i++) {
1980
6.25M
            sha256->digest[i] += S[i];
1981
6.25M
        }
1982
1983
        /* W and S are the caller's Sha256TScratch, wiped with one ForceZero
1984
         * when the public call returns. */
1985
782k
        return 0;
1986
782k
    }
1987
#else
1988
    /* SHA256 version that keeps all data in registers */
1989
    #define SCHED1(j) (W[j] = *((word32*)&data[j*sizeof(word32)]))
1990
    #define SCHED(j) (               \
1991
                   W[ j     & 15] += \
1992
            Gamma1(W[(j-2)  & 15])+  \
1993
                   W[(j-7)  & 15] +  \
1994
            Gamma0(W[(j-15) & 15])   \
1995
        )
1996
1997
    #define RND1(j) \
1998
         t0 = h(j) + Sigma1(e(j)) + Ch(e(j), f(j), g(j)) + K[i+j] + SCHED1(j); \
1999
         t1 = Sigma0(a(j)) + Maj(a(j), b(j), c(j)); \
2000
         d(j) += t0; \
2001
         h(j)  = t0 + t1
2002
    #define RNDN(j) \
2003
         t0 = h(j) + Sigma1(e(j)) + Ch(e(j), f(j), g(j)) + K[i+j] + SCHED(j); \
2004
         t1 = Sigma0(a(j)) + Maj(a(j), b(j), c(j)); \
2005
         d(j) += t0; \
2006
         h(j)  = t0 + t1
2007
2008
    static int Transform_Sha256_scr(wc_Sha256* sha256, const byte* data,
2009
                                    Sha256TScratch* WC_RESTRICT scr)
2010
    {
2011
        word32 t0, t1;
2012
        int i;
2013
    #ifdef USE_SLOW_SHA256
2014
        int j;
2015
    #endif
2016
        word32* WC_RESTRICT W = scr->W;
2017
        word32* WC_RESTRICT S = scr->S;
2018
2019
        /* Copy digest to working vars */
2020
        S[0] = sha256->digest[0];
2021
        S[1] = sha256->digest[1];
2022
        S[2] = sha256->digest[2];
2023
        S[3] = sha256->digest[3];
2024
        S[4] = sha256->digest[4];
2025
        S[5] = sha256->digest[5];
2026
        S[6] = sha256->digest[6];
2027
        S[7] = sha256->digest[7];
2028
2029
        i = 0;
2030
    #ifdef USE_SLOW_SHA256
2031
        for (j = 0; j < 16; j++) {
2032
            RND1(j);
2033
        }
2034
        for (i = 16; i < 64; i += 16) {
2035
            for (j = 0; j < 16; j++) {
2036
                RNDN(j);
2037
            }
2038
        }
2039
    #else
2040
        RND1( 0); RND1( 1); RND1( 2); RND1( 3);
2041
        RND1( 4); RND1( 5); RND1( 6); RND1( 7);
2042
        RND1( 8); RND1( 9); RND1(10); RND1(11);
2043
        RND1(12); RND1(13); RND1(14); RND1(15);
2044
        /* 64 operations, partially loop unrolled */
2045
        for (i = 16; i < 64; i += 16) {
2046
            RNDN( 0); RNDN( 1); RNDN( 2); RNDN( 3);
2047
            RNDN( 4); RNDN( 5); RNDN( 6); RNDN( 7);
2048
            RNDN( 8); RNDN( 9); RNDN(10); RNDN(11);
2049
            RNDN(12); RNDN(13); RNDN(14); RNDN(15);
2050
        }
2051
    #endif
2052
2053
        /* Add the working vars back into digest */
2054
        sha256->digest[0] += S[0];
2055
        sha256->digest[1] += S[1];
2056
        sha256->digest[2] += S[2];
2057
        sha256->digest[3] += S[3];
2058
        sha256->digest[4] += S[4];
2059
        sha256->digest[5] += S[5];
2060
        sha256->digest[6] += S[6];
2061
        sha256->digest[7] += S[7];
2062
2063
        /* W and S are the caller's Sha256TScratch, wiped with one ForceZero
2064
         * when the public call returns. */
2065
        return 0;
2066
    }
2067
#endif /* SHA256_MANY_REGISTERS */
2068
2069
    /* Compatibility entry with per-call scratch, for the dispatch arms,
2070
     * function-pointer tables, and single-block callers, all of whose
2071
     * signatures stay unchanged.  Bulk callers hoist one scratch across
2072
     * their block loop and call Transform_Sha256_scr() directly, so the
2073
     * wipe runs once per public call rather than once per block. */
2074
    static WC_MAYBE_UNUSED int Transform_Sha256(wc_Sha256* sha256,
2075
                                                const byte* data)
2076
716k
    {
2077
716k
        int ret;
2078
716k
        WC_SHA256_TSCRATCH_DECL(sha256);
2079
716k
        WC_SHA256_TSCRATCH_BEGIN(sha256);
2080
716k
        ret = Transform_Sha256_scr(sha256, data, sha256TScr);
2081
716k
        WC_SHA256_TSCRATCH_WIPE(sha256);
2082
716k
        return ret;
2083
716k
    }
2084
#endif
2085
/* End wc_ software implementation */
2086
2087
#if defined(WOLFSSL_HAVE_SHA256_HASH_BLOCK) && !defined(XTRANSFORM)
2088
    #error "WOLFSSL_HAVE_SHA256_HASH_BLOCK set without a SHA-256 transform"
2089
#endif
2090
2091
#ifdef XTRANSFORM
2092
2093
    static WC_INLINE void AddLength(wc_Sha256* sha256, word32 len)
2094
443k
    {
2095
443k
        word32 tmp = sha256->loLen;
2096
443k
        if ((sha256->loLen += len) < tmp) {
2097
0
            sha256->hiLen++;                       /* carry low to high */
2098
0
        }
2099
443k
    }
2100
2101
    /* do block size increments/updates */
2102
    static WC_INLINE int Sha256Update(wc_Sha256* sha256, const byte* data,
2103
        word32 len)
2104
443k
    {
2105
443k
        int ret = 0;
2106
443k
        word32 blocksLen;
2107
443k
        byte* local;
2108
2109
        /* check that internal buffLen is valid */
2110
443k
        if (sha256->buffLen >= WC_SHA256_BLOCK_SIZE) {
2111
0
            return BUFFER_E;
2112
0
        }
2113
2114
        /* add length for final */
2115
443k
        AddLength(sha256, len);
2116
2117
443k
        local = (byte*)sha256->buffer;
2118
2119
        /* process any remainder from previous operation */
2120
443k
        if (sha256->buffLen > 0) {
2121
223k
            blocksLen = min(len, WC_SHA256_BLOCK_SIZE - sha256->buffLen);
2122
223k
            XMEMCPY(&local[sha256->buffLen], data, blocksLen);
2123
2124
223k
            sha256->buffLen += blocksLen;
2125
223k
            data            += blocksLen;
2126
223k
            len             -= blocksLen;
2127
2128
223k
            if (sha256->buffLen == WC_SHA256_BLOCK_SIZE) {
2129
            #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2130
               !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2131
                if (sha256->ctx.mode == ESP32_SHA_INIT) {
2132
                    ESP_LOGV(TAG, "Sha256Update try hardware");
2133
                    esp_sha_try_hw_lock(&sha256->ctx);
2134
                }
2135
            #endif
2136
2137
55.0k
            if (SHA256_UPDATE_REV_BYTES(&sha256->ctx)) {
2138
            #ifdef WOLFSSL_WIDE_BYTE
2139
                /* CHAR_BIT != 8: pack 16 big-endian schedule words octet-wise */
2140
                WordsFromBytesBE32(sha256->buffer, (const byte*)sha256->buffer,
2141
                    WC_SHA256_BLOCK_SIZE / 4);
2142
            #else
2143
55.0k
                ByteReverseWords(sha256->buffer, sha256->buffer,
2144
55.0k
                    WC_SHA256_BLOCK_SIZE);
2145
55.0k
            #endif
2146
55.0k
            }
2147
2148
            #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2149
               !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2150
                if (sha256->ctx.mode == ESP32_SHA_SW) {
2151
                    #if defined(WOLFSSL_DEBUG_MUTEX)
2152
                    {
2153
                        ESP_LOGI(TAG, "Sha256Update process software");
2154
                    }
2155
                    #endif
2156
                    #ifdef WOLFSSL_HW_METRICS
2157
                    {
2158
                        /* Track of # SW during transforms during active HW */
2159
                        esp_sw_sha256_count_add();
2160
                    }
2161
                    #endif /* WOLFSSL_HW_METRICS */
2162
                    ret = XTRANSFORM(sha256, (const byte*)local);
2163
                }
2164
                else {
2165
                    #if defined(WOLFSSL_DEBUG_MUTEX)
2166
                    {
2167
                        ESP_LOGI(TAG, "Sha256Update process hardware");
2168
                    }
2169
                    #endif
2170
                    esp_sha256_process(sha256, (const byte*)local);
2171
                }
2172
            #else
2173
                /* Always SW */
2174
55.0k
                ret = XTRANSFORM(sha256, (const byte*)local);
2175
55.0k
            #endif
2176
55.0k
                if (ret == 0)
2177
55.0k
                    sha256->buffLen = 0;
2178
11
                else
2179
11
                    len = 0; /* error */
2180
55.0k
            }
2181
223k
        }
2182
2183
        /* process blocks */
2184
    #ifdef XTRANSFORM_LEN
2185
        #if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
2186
                          (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))
2187
2188
        #ifdef WC_NO_INTERNAL_FUNCTION_POINTERS
2189
        if (sha_method != SHA256_C)
2190
        #else
2191
        if (Transform_Sha256_Len_p != NULL)
2192
        #endif
2193
2194
        #endif
2195
        {
2196
            if (len >= WC_SHA256_BLOCK_SIZE) {
2197
                /* get number of blocks */
2198
                /* 64-1 = 0x3F (~ Inverted = 0xFFFFFFC0) */
2199
                /* len (masked by 0xFFFFFFC0) returns block aligned length */
2200
                blocksLen = len & ~((word32)WC_SHA256_BLOCK_SIZE-1);
2201
                /* Byte reversal and alignment handled in function if required
2202
                 */
2203
                ret = XTRANSFORM_LEN(sha256, data, blocksLen);
2204
                if (ret == 0) {
2205
                    data += blocksLen;
2206
                    len  -= blocksLen;
2207
                }
2208
            }
2209
        }
2210
        #if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
2211
                          (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))
2212
        else
2213
        #endif
2214
    #endif /* XTRANSFORM_LEN */
2215
443k
    #if !defined(XTRANSFORM_LEN) || \
2216
443k
        (defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
2217
443k
         (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2)))
2218
443k
        {
2219
1.05M
            while (len >= WC_SHA256_BLOCK_SIZE) {
2220
614k
                word32* local32 = sha256->buffer;
2221
                /* optimization to avoid memcpy if data pointer is properly aligned */
2222
                /* Intel transform function requires use of sha256->buffer */
2223
                /* Little Endian requires byte swap, so can't use data directly */
2224
            #if defined(WC_HASH_DATA_ALIGNMENT) && !defined(LITTLE_ENDIAN_ORDER) && \
2225
                !(defined(WOLFSSL_X86_64_BUILD) && \
2226
                         defined(USE_INTEL_SPEEDUP) && \
2227
                         (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2)))
2228
                if (((wc_ptr_t)data % WC_HASH_DATA_ALIGNMENT) == 0) {
2229
                    local32 = (word32*)data;
2230
                }
2231
                else
2232
            #endif
2233
614k
                {
2234
614k
                    XMEMCPY(local32, data, WC_SHA256_BLOCK_SIZE);
2235
614k
                }
2236
2237
614k
                data += WC_SHA256_BLOCK_SIZE;
2238
614k
                len  -= WC_SHA256_BLOCK_SIZE;
2239
            #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2240
               !defined( NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2241
                if (sha256->ctx.mode == ESP32_SHA_INIT){
2242
                    ESP_LOGV(TAG, "Sha256Update try hardware loop");
2243
                    esp_sha_try_hw_lock(&sha256->ctx);
2244
                }
2245
            #endif
2246
2247
614k
            if (SHA256_UPDATE_REV_BYTES(&sha256->ctx)) {
2248
            #ifdef WOLFSSL_WIDE_BYTE
2249
                WordsFromBytesBE32(local32, (const byte*)local32,
2250
                    WC_SHA256_BLOCK_SIZE / 4);
2251
            #else
2252
614k
                ByteReverseWords(local32, local32, WC_SHA256_BLOCK_SIZE);
2253
614k
            #endif
2254
614k
            }
2255
2256
            #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2257
               !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2258
                if (sha256->ctx.mode == ESP32_SHA_SW) {
2259
                    ESP_LOGV(TAG, "Sha256Update process software loop");
2260
                    ret = XTRANSFORM(sha256, (const byte*)local32);
2261
                }
2262
                else {
2263
                    ESP_LOGV(TAG, "Sha256Update process hardware");
2264
                    esp_sha256_process(sha256, (const byte*)local32);
2265
                }
2266
            #else
2267
614k
                ret = XTRANSFORM(sha256, (const byte*)local32);
2268
614k
            #endif
2269
2270
614k
                if (ret != 0)
2271
36
                    break;
2272
614k
            }
2273
443k
        }
2274
443k
    #endif
2275
2276
        /* save remainder */
2277
443k
        if (ret == 0 && len > 0) {
2278
174k
            XMEMCPY(local, data, len);
2279
174k
            sha256->buffLen = len;
2280
174k
        }
2281
2282
443k
        return ret;
2283
443k
    }
2284
2285
#if defined(WOLFSSL_KCAPI_HASH)
2286
    /* implemented in wolfcrypt/src/port/kcapi/kcapi_hash.c */
2287
2288
#else
2289
    int wc_Sha256Update(wc_Sha256* sha256, const byte* data, word32 len)
2290
433k
    {
2291
433k
        if (sha256 == NULL) {
2292
0
            return BAD_FUNC_ARG;
2293
0
        }
2294
433k
        if (len == 0) {
2295
            /* valid, but do nothing */
2296
4.52k
            return 0;
2297
4.52k
        }
2298
428k
        if (data == NULL) {
2299
0
            return BAD_FUNC_ARG;
2300
0
        }
2301
2302
428k
    #ifdef WOLF_CRYPTO_CB
2303
428k
        #ifndef WOLF_CRYPTO_CB_FIND
2304
428k
        if (sha256->devId != INVALID_DEVID)
2305
106
        #endif
2306
106
        {
2307
106
            int ret = wc_CryptoCb_Sha256Hash(sha256, data, len, NULL);
2308
106
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
2309
0
                return ret;
2310
            /* fall-through when unavailable */
2311
106
        }
2312
428k
    #endif
2313
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256)
2314
        if (sha256->asyncDev.marker == WOLFSSL_ASYNC_MARKER_SHA256) {
2315
        #if defined(HAVE_INTEL_QA)
2316
            return IntelQaSymSha256(&sha256->asyncDev, NULL, data, len);
2317
        #endif
2318
        }
2319
    #endif /* WOLFSSL_ASYNC_CRYPT */
2320
2321
428k
        return Sha256Update(sha256, data, len);
2322
428k
    }
2323
#endif
2324
2325
    static WC_INLINE int Sha256Final(wc_Sha256* sha256)
2326
112k
    {
2327
112k
        int ret;
2328
112k
        byte* local;
2329
2330
        /* we'll add a 0x80 byte at the end,
2331
        ** so make sure we have appropriate buffer length. */
2332
112k
        if (sha256->buffLen > WC_SHA256_BLOCK_SIZE - 1) {
2333
            /* exit with error code if there's a bad buffer size in buffLen */
2334
0
            return BAD_STATE_E;
2335
0
        } /* buffLen check */
2336
2337
112k
        local = (byte*)sha256->buffer;
2338
112k
        local[sha256->buffLen++] = 0x80; /* add 1 */
2339
2340
        /* pad with zeros */
2341
112k
        if (sha256->buffLen > WC_SHA256_PAD_SIZE) {
2342
755
            if (sha256->buffLen < WC_SHA256_BLOCK_SIZE) {
2343
664
                XMEMSET(&local[sha256->buffLen], 0,
2344
664
                    WC_SHA256_BLOCK_SIZE - sha256->buffLen);
2345
664
            }
2346
2347
        #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2348
           !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2349
            if (sha256->ctx.mode == ESP32_SHA_INIT) {
2350
                esp_sha_try_hw_lock(&sha256->ctx);
2351
            }
2352
        #endif
2353
2354
755
        if (SHA256_UPDATE_REV_BYTES(&sha256->ctx)) {
2355
        #ifdef WOLFSSL_WIDE_BYTE
2356
            WordsFromBytesBE32(sha256->buffer, (const byte*)sha256->buffer,
2357
                WC_SHA256_BLOCK_SIZE / 4);
2358
        #else
2359
755
            ByteReverseWords(sha256->buffer, sha256->buffer,
2360
755
                WC_SHA256_BLOCK_SIZE);
2361
755
        #endif
2362
755
        }
2363
2364
        #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2365
           !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2366
            if (sha256->ctx.mode == ESP32_SHA_INIT) {
2367
                esp_sha_try_hw_lock(&sha256->ctx);
2368
            }
2369
            if (sha256->ctx.mode == ESP32_SHA_SW) {
2370
                ret = XTRANSFORM(sha256, (const byte*)local);
2371
            }
2372
            else {
2373
                ret = esp_sha256_process(sha256, (const byte*)local);
2374
            }
2375
        #else
2376
755
            ret = XTRANSFORM(sha256, (const byte*)local);
2377
755
        #endif
2378
755
            if (ret != 0)
2379
0
                return ret;
2380
2381
755
            sha256->buffLen = 0;
2382
755
        }
2383
112k
        XMEMSET(&local[sha256->buffLen], 0,
2384
112k
            WC_SHA256_PAD_SIZE - sha256->buffLen);
2385
2386
        /* put 64 bit length in separate 32 bit parts */
2387
112k
        sha256->hiLen = (sha256->loLen >>
2388
112k
                            (CHAR_BIT * sizeof(sha256->loLen) - 3)) +
2389
112k
                                                         (sha256->hiLen << 3);
2390
112k
        sha256->loLen = sha256->loLen << 3;
2391
2392
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2393
       !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2394
        if (sha256->ctx.mode == ESP32_SHA_INIT) {
2395
            esp_sha_try_hw_lock(&sha256->ctx);
2396
        }
2397
    #endif
2398
2399
        /* store lengths */
2400
#ifdef WOLFSSL_WIDE_BYTE
2401
        /* CHAR_BIT != 8: 'local' indexes octet cells, so place the 64-bit
2402
         * bit-length as 8 big-endian octets (W[14]=hiLen, W[15]=loLen). */
2403
        local[WC_SHA256_PAD_SIZE + 0] = (byte)((sha256->hiLen >> 24) & 0xFF);
2404
        local[WC_SHA256_PAD_SIZE + 1] = (byte)((sha256->hiLen >> 16) & 0xFF);
2405
        local[WC_SHA256_PAD_SIZE + 2] = (byte)((sha256->hiLen >>  8) & 0xFF);
2406
        local[WC_SHA256_PAD_SIZE + 3] = (byte)((sha256->hiLen      ) & 0xFF);
2407
        local[WC_SHA256_PAD_SIZE + 4] = (byte)((sha256->loLen >> 24) & 0xFF);
2408
        local[WC_SHA256_PAD_SIZE + 5] = (byte)((sha256->loLen >> 16) & 0xFF);
2409
        local[WC_SHA256_PAD_SIZE + 6] = (byte)((sha256->loLen >>  8) & 0xFF);
2410
        local[WC_SHA256_PAD_SIZE + 7] = (byte)((sha256->loLen      ) & 0xFF);
2411
#endif
2412
112k
        if (SHA256_UPDATE_REV_BYTES(&sha256->ctx)) {
2413
        #ifdef WOLFSSL_WIDE_BYTE
2414
            /* pack all 16 big-endian schedule words octet-wise (incl. length) */
2415
            WordsFromBytesBE32(sha256->buffer, (const byte*)sha256->buffer,
2416
                WC_SHA256_BLOCK_SIZE / 4);
2417
        #else
2418
112k
            ByteReverseWords(sha256->buffer, sha256->buffer,
2419
112k
                WC_SHA256_PAD_SIZE);
2420
112k
        #endif
2421
112k
        }
2422
112k
#ifndef WOLFSSL_WIDE_BYTE
2423
        /* ! 64-bit length ordering dependent on digest endian type ! */
2424
112k
        XMEMCPY(&local[WC_SHA256_PAD_SIZE], &sha256->hiLen, sizeof(word32));
2425
112k
        XMEMCPY(&local[WC_SHA256_PAD_SIZE + sizeof(word32)], &sha256->loLen,
2426
112k
                sizeof(word32));
2427
112k
#endif
2428
2429
    /* Only the ESP32-C3 with HW enabled may need pad size byte order reversal
2430
     * depending on HW or SW mode */
2431
    #if ( defined(CONFIG_IDF_TARGET_ESP32C2) || \
2432
          defined(CONFIG_IDF_TARGET_ESP8684) || \
2433
          defined(CONFIG_IDF_TARGET_ESP32C3) || \
2434
          defined(CONFIG_IDF_TARGET_ESP32C6)    \
2435
        ) && \
2436
        defined(WOLFSSL_ESP32_CRYPT) &&         \
2437
       !defined(NO_WOLFSSL_ESP32_CRYPT_HASH) && \
2438
       !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2439
        /* For Espressif RISC-V Targets, we *may* need to reverse bytes
2440
         * depending on if HW is active or not. */
2441
        if (sha256->ctx.mode == ESP32_SHA_HW) {
2442
        #if defined(WOLFSSL_SUPER_VERBOSE_DEBUG)
2443
            ESP_LOGV(TAG, "Start: Reverse PAD SIZE Endianness.");
2444
        #endif
2445
            ByteReverseWords(
2446
                &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)], /* out */
2447
                &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)], /* in  */
2448
                2 * sizeof(word32) /* byte count to reverse */
2449
            );
2450
        #if defined(WOLFSSL_SUPER_VERBOSE_DEBUG)
2451
            ESP_LOGV(TAG, "End: Reverse PAD SIZE Endianness.");
2452
        #endif
2453
        } /* end if (sha256->ctx.mode == ESP32_SHA_HW) */
2454
    #endif
2455
2456
    #if defined(FREESCALE_MMCAU_SHA) || \
2457
        (defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
2458
                         (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2)))
2459
        /* Kinetis requires only these bytes reversed */
2460
        #if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
2461
                          (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))
2462
        #ifdef WC_SHA256_RAW_BE_BUFFER
2463
        /* raw-buffer convention -- the length words must be big-endian in the
2464
         * stream regardless of which transform consumes the final block. */
2465
        #else
2466
        if (IS_INTEL_AVX1(intel_flags) || IS_INTEL_AVX2(intel_flags) ||
2467
            IS_INTEL_SHA(intel_flags))
2468
        #endif
2469
        #endif
2470
        {
2471
            ByteReverseWords(
2472
                &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)],
2473
                &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)],
2474
                2 * sizeof(word32));
2475
        }
2476
    #endif
2477
    #if (defined(WOLFSSL_ARMASM) || defined(WOLFSSL_RISCV_ASM)) && \
2478
        !defined(FREESCALE_MMCAU_SHA)
2479
        ByteReverseWords( &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)],
2480
            &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)],
2481
            2 * sizeof(word32));
2482
    #endif
2483
    #if defined(WOLFSSL_PPC64_ASM) && defined(LITTLE_ENDIAN_ORDER)
2484
        /* The PPC64 assembly loads the message with byte-reversed loads on
2485
         * little-endian, treating the whole block as a big-endian byte stream.
2486
         * The 64-bit length above is stored in native (little-endian) word
2487
         * order, so reverse it here to keep the block a consistent big-endian
2488
         * stream. */
2489
        ByteReverseWords( &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)],
2490
            &sha256->buffer[WC_SHA256_PAD_SIZE / sizeof(word32)],
2491
            2 * sizeof(word32));
2492
    #endif
2493
2494
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
2495
       !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
2496
        if (sha256->ctx.mode == ESP32_SHA_INIT) {
2497
            esp_sha_try_hw_lock(&sha256->ctx);
2498
        }
2499
        /* depending on architecture and ctx.mode value
2500
         * we may or may not need default digest */
2501
        if (sha256->ctx.mode == ESP32_SHA_SW) {
2502
            ret = XTRANSFORM(sha256, (const byte*)local);
2503
        }
2504
        else {
2505
            ret = esp_sha256_digest_process(sha256, 1);
2506
        }
2507
    #else
2508
112k
        ret = XTRANSFORM(sha256, (const byte*)local);
2509
112k
    #endif
2510
2511
112k
        return ret;
2512
112k
    }
2513
2514
#if !defined(WOLFSSL_KCAPI_HASH)
2515
2516
#ifndef WOLF_CRYPTO_CB_ONLY_SHA256
2517
    int wc_Sha256FinalRaw(wc_Sha256* sha256, byte* hash)
2518
145
    {
2519
145
    #if defined(LITTLE_ENDIAN_ORDER) && !defined(WOLFSSL_WIDE_BYTE)
2520
145
        word32 digest[WC_SHA256_DIGEST_SIZE / sizeof(word32)];
2521
145
        XMEMSET(digest, 0, sizeof(digest));
2522
145
    #endif
2523
2524
145
        if (sha256 == NULL || hash == NULL) {
2525
0
            return BAD_FUNC_ARG;
2526
0
        }
2527
    #if defined(WOLFSSL_CHECK_MEM_ZERO) && defined(LITTLE_ENDIAN_ORDER) && \
2528
        !defined(WOLFSSL_WIDE_BYTE)
2529
        wc_MemZero_Add("wc_Sha256FinalRaw digest", digest, sizeof(digest));
2530
    #endif
2531
2532
    #if defined(WOLFSSL_WIDE_BYTE)
2533
        /* CHAR_BIT != 8: store digest words as big-endian octets. */
2534
        BytesFromWordsBE32(hash, sha256->digest, WC_SHA256_DIGEST_SIZE);
2535
    #elif defined(LITTLE_ENDIAN_ORDER)
2536
145
        if (SHA256_REV_BYTES(&sha256->ctx)) {
2537
145
            ByteReverseWords((word32*)digest, (word32*)sha256->digest,
2538
145
                              WC_SHA256_DIGEST_SIZE);
2539
145
        }
2540
145
        XMEMCPY(hash, digest, WC_SHA256_DIGEST_SIZE);
2541
145
        ForceZero(digest, sizeof(digest));
2542
    #ifdef WOLFSSL_CHECK_MEM_ZERO
2543
        wc_MemZero_Check(digest, sizeof(digest));
2544
    #endif
2545
    #else
2546
        XMEMCPY(hash, sha256->digest, WC_SHA256_DIGEST_SIZE);
2547
    #endif
2548
2549
145
        return 0;
2550
145
    }
2551
#endif /* !WOLF_CRYPTO_CB_ONLY_SHA256 */
2552
2553
    int wc_Sha256Final(wc_Sha256* sha256, byte* hash)
2554
108k
    {
2555
108k
        int ret;
2556
2557
108k
        if (sha256 == NULL || hash == NULL) {
2558
0
            return BAD_FUNC_ARG;
2559
0
        }
2560
2561
108k
    #ifdef WOLF_CRYPTO_CB
2562
108k
        #ifndef WOLF_CRYPTO_CB_FIND
2563
108k
        if (sha256->devId != INVALID_DEVID)
2564
31
        #endif
2565
31
        {
2566
31
            ret = wc_CryptoCb_Sha256Hash(sha256, NULL, 0, hash);
2567
31
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
2568
0
                return ret;
2569
            /* fall-through when unavailable */
2570
31
        }
2571
108k
    #endif
2572
2573
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256)
2574
        if (sha256->asyncDev.marker == WOLFSSL_ASYNC_MARKER_SHA256) {
2575
        #if defined(HAVE_INTEL_QA)
2576
            return IntelQaSymSha256(&sha256->asyncDev, hash, NULL,
2577
                                            WC_SHA256_DIGEST_SIZE);
2578
        #endif
2579
        }
2580
    #endif /* WOLFSSL_ASYNC_CRYPT */
2581
2582
108k
        ret = Sha256Final(sha256);
2583
108k
        if (ret != 0) {
2584
14
            return ret;
2585
14
        }
2586
2587
    #if defined(WOLFSSL_WIDE_BYTE)
2588
        /* CHAR_BIT != 8: store digest words as big-endian octets. */
2589
        BytesFromWordsBE32(hash, sha256->digest, WC_SHA256_DIGEST_SIZE);
2590
    #else
2591
108k
    #if defined(LITTLE_ENDIAN_ORDER)
2592
108k
        if (SHA256_REV_BYTES(&sha256->ctx)) {
2593
108k
            ByteReverseWords(sha256->digest, sha256->digest,
2594
108k
                WC_SHA256_DIGEST_SIZE);
2595
108k
        }
2596
108k
    #endif
2597
108k
        XMEMCPY(hash, sha256->digest, WC_SHA256_DIGEST_SIZE);
2598
108k
    #endif
2599
2600
108k
        return InitSha256(sha256);  /* reset state */
2601
108k
    }
2602
2603
#if defined(OPENSSL_EXTRA) || defined(HAVE_CURL)
2604
/* Apply SHA256 transformation to the data                */
2605
/* @param sha  a pointer to wc_Sha256 structure           */
2606
/* @param data data to be applied SHA256 transformation   */
2607
/* @return 0 on successful, otherwise non-zero on failure */
2608
    int wc_Sha256Transform(wc_Sha256* sha256, const unsigned char* data)
2609
    {
2610
        if (sha256 == NULL || data == NULL) {
2611
            return BAD_FUNC_ARG;
2612
        }
2613
2614
    #if defined(WOLFSSL_ARMASM) || defined(WOLFSSL_RISCV_ASM) || \
2615
        (defined(WOLFSSL_PPC64_ASM) && defined(LITTLE_ENDIAN_ORDER))
2616
        #ifdef __aarch64__
2617
        if (Transform_Sha256_Len_p == Transform_Sha256_Len) {
2618
            return Transform_Sha256(sha256, data);
2619
        }
2620
        else
2621
        #endif
2622
        {
2623
            byte buffer[WC_SHA256_BLOCK_SIZE];
2624
            int tret;
2625
        #ifdef WOLFSSL_CHECK_MEM_ZERO
2626
            wc_MemZero_Add("wc_Sha256Transform buffer", buffer,
2627
                sizeof(buffer));
2628
        #endif
2629
            ByteReverseWords((word32*)buffer, (word32*)data,
2630
                WC_SHA256_BLOCK_SIZE);
2631
        #ifdef __aarch64__
2632
            tret = Transform_Sha256_aarch64(sha256, buffer);
2633
        #else
2634
            tret = Transform_Sha256(sha256, buffer);
2635
        #endif
2636
            ForceZero(buffer, sizeof(buffer));
2637
        #ifdef WOLFSSL_CHECK_MEM_ZERO
2638
            wc_MemZero_Check(buffer, sizeof(buffer));
2639
        #endif
2640
            return tret;
2641
        }
2642
    #else
2643
        return Transform_Sha256(sha256, data);
2644
    #endif
2645
    }
2646
#endif /* OPENSSL_EXTRA || HAVE_CURL */
2647
2648
#ifdef WOLFSSL_HAVE_SHA256_HASH_BLOCK
2649
    /* One block will be used from data.
2650
     * hash must be big enough to hold all of digest output.
2651
     */
2652
    int wc_Sha256HashBlock(wc_Sha256* sha256, const unsigned char* data,
2653
        unsigned char* hash)
2654
    {
2655
        int ret;
2656
2657
        if ((sha256 == NULL) || (data == NULL)) {
2658
            return BAD_FUNC_ARG;
2659
        }
2660
2661
        if (SHA256_UPDATE_REV_BYTES(&sha256->ctx)) {
2662
        #ifdef WOLFSSL_WIDE_BYTE
2663
            /* CHAR_BIT != 8: pack 16 big-endian schedule words octet-wise */
2664
            WordsFromBytesBE32(sha256->buffer, data,
2665
                WC_SHA256_BLOCK_SIZE / 4);
2666
        #else
2667
            /* Reverse in place. Stage first only when data is the caller's
2668
             * own buffer, which may be unaligned - LMS hands us
2669
             * sha256->buffer itself, and copying that onto itself is UB. */
2670
            if (data != (const unsigned char*)sha256->buffer) {
2671
                XMEMCPY(sha256->buffer, data, WC_SHA256_BLOCK_SIZE);
2672
            }
2673
            ByteReverseWords(sha256->buffer, sha256->buffer,
2674
                WC_SHA256_BLOCK_SIZE);
2675
        #endif
2676
            data = (const unsigned char*)sha256->buffer;
2677
        }
2678
        ret = XTRANSFORM(sha256, data);
2679
2680
        if ((ret == 0) && (hash != NULL)) {
2681
            if (!SHA256_REV_BYTES(&sha256->ctx)) {
2682
                XMEMCPY(hash, sha256->digest, WC_SHA256_DIGEST_SIZE);
2683
            }
2684
        #if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP)
2685
            else if (!IS_INTEL_MOVBE(cpuid_get_flags())) {
2686
                /* No MOVBE: reverse into aligned buffer, hash may be
2687
                 * unaligned. */
2688
                word32 buf[WC_SHA256_DIGEST_SIZE / sizeof(word32)];
2689
                ByteReverseWords(buf, sha256->digest, WC_SHA256_DIGEST_SIZE);
2690
                XMEMCPY(hash, buf, WC_SHA256_DIGEST_SIZE);
2691
                ForceZero(buf, sizeof(buf));
2692
            }
2693
        #endif
2694
            else {
2695
        #if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP)
2696
                __asm__ __volatile__ (
2697
                    "mov    0x00(%[d]), %%esi\n\t"
2698
                    "movbe  %%esi, 0x00(%[h])\n\t"
2699
                    "mov    0x04(%[d]), %%esi\n\t"
2700
                    "movbe  %%esi, 0x04(%[h])\n\t"
2701
                    "mov    0x08(%[d]), %%esi\n\t"
2702
                    "movbe  %%esi, 0x08(%[h])\n\t"
2703
                    "mov    0x0c(%[d]), %%esi\n\t"
2704
                    "movbe  %%esi, 0x0c(%[h])\n\t"
2705
                    "mov    0x10(%[d]), %%esi\n\t"
2706
                    "movbe  %%esi, 0x10(%[h])\n\t"
2707
                    "mov    0x14(%[d]), %%esi\n\t"
2708
                    "movbe  %%esi, 0x14(%[h])\n\t"
2709
                    "mov    0x18(%[d]), %%esi\n\t"
2710
                    "movbe  %%esi, 0x18(%[h])\n\t"
2711
                    "mov    0x1c(%[d]), %%esi\n\t"
2712
                    "movbe  %%esi, 0x1c(%[h])\n\t"
2713
                    :
2714
                    : [d] "r" (sha256->digest), [h] "r" (hash)
2715
                    : "memory", "esi"
2716
                );
2717
        #else
2718
                word32* hash32 = (word32*)hash;
2719
                word32* digest = (word32*)sha256->digest;
2720
            #if WOLFSSL_GENERAL_ALIGNMENT < 4
2721
                ALIGN16 word32 buf[WC_SHA256_DIGEST_SIZE / sizeof(word32)];
2722
2723
                if (((size_t)digest & 0x3) != 0) {
2724
                    if (((size_t)hash32 & 0x3) != 0) {
2725
                        XMEMCPY(buf, digest, WC_SHA256_DIGEST_SIZE);
2726
                        hash32 = buf;
2727
                        digest = buf;
2728
                    }
2729
                    else {
2730
                        XMEMCPY(hash, digest, WC_SHA256_DIGEST_SIZE);
2731
                        digest = hash32;
2732
                    }
2733
                }
2734
                else if (((size_t)hash32 & 0x3) != 0) {
2735
                    hash32 = digest;
2736
                }
2737
            #endif
2738
                ByteReverseWords(hash32, digest, (word32)(sizeof(word32) * 8));
2739
            #if WOLFSSL_GENERAL_ALIGNMENT < 4
2740
                if (hash != (byte*)hash32) {
2741
                    XMEMCPY(hash, hash32, WC_SHA256_DIGEST_SIZE);
2742
                }
2743
            #endif
2744
        #endif /* WOLFSSL_X86_64_BUILD && USE_INTEL_SPEEDUP */
2745
            }
2746
            sha256->digest[0] = 0x6A09E667L;
2747
            sha256->digest[1] = 0xBB67AE85L;
2748
            sha256->digest[2] = 0x3C6EF372L;
2749
            sha256->digest[3] = 0xA54FF53AL;
2750
            sha256->digest[4] = 0x510E527FL;
2751
            sha256->digest[5] = 0x9B05688CL;
2752
            sha256->digest[6] = 0x1F83D9ABL;
2753
            sha256->digest[7] = 0x5BE0CD19L;
2754
        }
2755
2756
        return ret;
2757
    }
2758
#endif /* WOLFSSL_HAVE_SHA256_HASH_BLOCK */
2759
#endif /* !WOLFSSL_KCAPI_HASH */
2760
2761
#endif /* XTRANSFORM */
2762
2763
#ifdef WOLF_CRYPTO_CB_ONLY_SHA256
2764
2765
    int wc_Sha256Update(wc_Sha256* sha256, const byte* data, word32 len)
2766
    {
2767
        if (sha256 == NULL) {
2768
            return BAD_FUNC_ARG;
2769
        }
2770
        if (data == NULL && len == 0) {
2771
            /* valid, but do nothing */
2772
            return 0;
2773
        }
2774
        if (data == NULL) {
2775
            return BAD_FUNC_ARG;
2776
        }
2777
2778
        #ifndef WOLF_CRYPTO_CB_FIND
2779
        if (sha256->devId != INVALID_DEVID)
2780
        #endif
2781
        {
2782
            int ret = wc_CryptoCb_Sha256Hash(sha256, data, len, NULL);
2783
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
2784
                return ret;
2785
        }
2786
2787
        return NO_VALID_DEVID;
2788
    }
2789
2790
    int wc_Sha256Final(wc_Sha256* sha256, byte* hash)
2791
    {
2792
        int ret;
2793
2794
        if (sha256 == NULL || hash == NULL) {
2795
            return BAD_FUNC_ARG;
2796
        }
2797
2798
        #ifndef WOLF_CRYPTO_CB_FIND
2799
        if (sha256->devId != INVALID_DEVID)
2800
        #endif
2801
        {
2802
            ret = wc_CryptoCb_Sha256Hash(sha256, NULL, 0, hash);
2803
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
2804
                return ret;
2805
        }
2806
2807
        return NO_VALID_DEVID;
2808
    }
2809
2810
#endif /* WOLF_CRYPTO_CB_ONLY_SHA256 */
2811
2812
2813
#ifdef WOLFSSL_SHA224
2814
2815
#ifdef STM32_HASH_SHA2
2816
2817
    /* Supports CubeMX HAL or Standard Peripheral Library */
2818
2819
    int wc_InitSha224_ex(wc_Sha224* sha224, void* heap, int devId)
2820
    {
2821
        if (sha224 == NULL)
2822
            return BAD_FUNC_ARG;
2823
        WC_SILABS_CLEAR_HASH_CTX(sha224);
2824
        (void)devId;
2825
        (void)heap;
2826
2827
        XMEMSET(sha224, 0, sizeof(wc_Sha224));
2828
        wc_Stm32_Hash_Init(&sha224->stmCtx);
2829
        return 0;
2830
    }
2831
2832
    int wc_Sha224Update(wc_Sha224* sha224, const byte* data, word32 len)
2833
    {
2834
        int ret = 0;
2835
2836
        if (sha224 == NULL || (data == NULL && len > 0)) {
2837
            return BAD_FUNC_ARG;
2838
        }
2839
2840
        ret = wolfSSL_CryptHwMutexLock();
2841
        if (ret == 0) {
2842
            ret = wc_Stm32_Hash_Update(&sha224->stmCtx,
2843
                HASH_AlgoSelection_SHA224, data, len, WC_SHA224_BLOCK_SIZE);
2844
            wolfSSL_CryptHwMutexUnLock();
2845
        }
2846
        return ret;
2847
    }
2848
2849
    int wc_Sha224Final(wc_Sha224* sha224, byte* hash)
2850
    {
2851
        int ret = 0;
2852
2853
        if (sha224 == NULL || hash == NULL) {
2854
            return BAD_FUNC_ARG;
2855
        }
2856
2857
        ret = wolfSSL_CryptHwMutexLock();
2858
        if (ret == 0) {
2859
            ret = wc_Stm32_Hash_Final(&sha224->stmCtx,
2860
                HASH_AlgoSelection_SHA224, hash, WC_SHA224_DIGEST_SIZE);
2861
            wolfSSL_CryptHwMutexUnLock();
2862
        }
2863
2864
        (void)wc_InitSha224(sha224); /* reset state */
2865
2866
        return ret;
2867
    }
2868
#elif defined(WOLFSSL_SE050) && defined(WOLFSSL_SE050_HASH)
2869
2870
    int wc_InitSha224_ex(wc_Sha224* sha224, void* heap, int devId)
2871
    {
2872
        if (sha224 == NULL) {
2873
            return BAD_FUNC_ARG;
2874
        }
2875
    #ifdef WC_CTX_IS_ALIGNED
2876
        if (!WC_CTX_IS_ALIGNED(sha224, wc_Sha224)) {
2877
            return BAD_ALIGN_E;
2878
        }
2879
    #endif
2880
        WC_SILABS_CLEAR_HASH_CTX(sha224);
2881
        (void)devId;
2882
2883
        return se050_hash_init(&sha224->se050Ctx, heap);
2884
    }
2885
2886
    int wc_Sha224Update(wc_Sha224* sha224, const byte* data, word32 len)
2887
    {
2888
        return se050_hash_update(&sha224->se050Ctx, data, len);
2889
    }
2890
2891
    int wc_Sha224Final(wc_Sha224* sha224, byte* hash)
2892
    {
2893
        int ret = 0;
2894
        ret = se050_hash_final(&sha224->se050Ctx, hash, WC_SHA224_DIGEST_SIZE,
2895
                               kAlgorithm_SSS_SHA224);
2896
        (void)wc_InitSha224(sha224);
2897
        return ret;
2898
    }
2899
2900
#elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_HASH) && \
2901
    !defined(WOLFSSL_QNX_CAAM)
2902
    /* functions defined in wolfcrypt/src/port/caam/caam_sha256.c */
2903
2904
#elif defined(WOLFSSL_AFALG_HASH)
2905
    #error SHA224 currently not supported with AF_ALG enabled
2906
2907
#elif defined(WOLFSSL_DEVCRYPTO_HASH)
2908
    /* implemented in wolfcrypt/src/port/devcrypto/devcrypt_hash.c */
2909
2910
#elif defined(WOLFSSL_SILABS_SE_ACCEL)
2911
    /* implemented in wolfcrypt/src/port/silabs/silabs_hash.c */
2912
2913
#elif defined(WOLFSSL_KCAPI_HASH) && !defined(WOLFSSL_NO_KCAPI_SHA224)
2914
    /* implemented in wolfcrypt/src/port/kcapi/kcapi_hash.c */
2915
2916
#elif defined(WOLFSSL_HAVE_PSA) && !defined(WOLFSSL_PSA_NO_HASH)
2917
    /* implemented in wolfcrypt/src/port/psa/psa_hash.c */
2918
2919
#elif defined(MAX3266X_SHA)
2920
    /* implemented in wolfcrypt/src/port/maxim/max3266x.c */
2921
2922
#elif defined(WOLFSSL_RENESAS_RX64_HASH)
2923
2924
/* implemented in wolfcrypt/src/port/Renesas/renesas_rx64_hw_sha.c */
2925
2926
#elif defined(WOLFSSL_RENESAS_RSIP) && \
2927
     !defined(NO_WOLFSSL_RENESAS_FSPSM_HASH)
2928
2929
    /* implemented in wolfcrypt/src/port/Renesas/renesas_fspsm_sha.c */
2930
#elif defined(PSOC6_HASH_SHA2)
2931
    /* Implemented in wolfcrypt/src/port/cypress/psoc6_crypto.c */
2932
2933
#elif defined(WOLF_CRYPTO_CB_ONLY_SHA256)
2934
    int wc_InitSha224_ex(wc_Sha224* sha224, void* heap, int devId)
2935
    {
2936
        int ret;
2937
        if (sha224 == NULL)
2938
            return BAD_FUNC_ARG;
2939
    #ifdef WC_CTX_IS_ALIGNED
2940
        if (!WC_CTX_IS_ALIGNED(sha224, wc_Sha224))
2941
            return BAD_ALIGN_E;
2942
    #endif
2943
        WC_SILABS_CLEAR_HASH_CTX(sha224);
2944
        ret = InitSha256((wc_Sha256*)sha224);
2945
        if (ret != 0)
2946
            return ret;
2947
        sha224->digest[0] = 0xc1059ed8;
2948
        sha224->digest[1] = 0x367cd507;
2949
        sha224->digest[2] = 0x3070dd17;
2950
        sha224->digest[3] = 0xf70e5939;
2951
        sha224->digest[4] = 0xffc00b31;
2952
        sha224->digest[5] = 0x68581511;
2953
        sha224->digest[6] = 0x64f98fa7;
2954
        sha224->digest[7] = 0xbefa4fa4;
2955
        sha224->heap   = heap;
2956
        sha224->devId  = devId;
2957
        sha224->devCtx = NULL;
2958
    #ifdef WOLFSSL_SMALL_STACK_CACHE
2959
        sha224->W = NULL;
2960
    #endif
2961
    #ifdef WOLFSSL_ASYNC_CRYPT
2962
        XMEMSET(&sha224->asyncDev, 0, sizeof(sha224->asyncDev));
2963
    #endif
2964
        return ret;
2965
    }
2966
2967
#else
2968
2969
    #define NEED_SOFT_SHA224
2970
2971
2972
    static int InitSha224(wc_Sha224* sha224)
2973
3.93k
    {
2974
3.93k
        int ret = 0;
2975
2976
#ifdef WOLFSSL_SMALL_STACK_CACHE
2977
    if (sha224->W == NULL) {
2978
        sha224->W = (word32*)XMALLOC(sizeof(Sha256TScratch),
2979
                                     sha224->heap, DYNAMIC_TYPE_DIGEST);
2980
        if (sha224->W == NULL)
2981
            return MEMORY_E;
2982
    }
2983
#endif
2984
2985
3.93k
        sha224->digest[0] = 0xc1059ed8;
2986
3.93k
        sha224->digest[1] = 0x367cd507;
2987
3.93k
        sha224->digest[2] = 0x3070dd17;
2988
3.93k
        sha224->digest[3] = 0xf70e5939;
2989
3.93k
        sha224->digest[4] = 0xffc00b31;
2990
3.93k
        sha224->digest[5] = 0x68581511;
2991
3.93k
        sha224->digest[6] = 0x64f98fa7;
2992
3.93k
        sha224->digest[7] = 0xbefa4fa4;
2993
2994
3.93k
        sha224->buffLen = 0;
2995
3.93k
        XMEMSET(sha224->buffer, 0, sizeof(sha224->buffer));
2996
3.93k
        sha224->loLen   = 0;
2997
3.93k
        sha224->hiLen   = 0;
2998
2999
    #if defined(WOLFSSL_X86_64_BUILD) && defined(USE_INTEL_SPEEDUP) && \
3000
                          (defined(HAVE_INTEL_AVX1) || defined(HAVE_INTEL_AVX2))
3001
        /* choose best Transform function under this runtime environment */
3002
        Sha256_SetTransform();
3003
    #elif defined(WOLFSSL_ARMASM_SHA256_TRANSFORM)
3004
        /* SHA-224 shares the SHA-256 transform, on AArch32 as well as AArch64;
3005
         * a no-op in builds that compile a single variant.  Keyed off the
3006
         * marker so the call cannot outlive its definition when a hardware
3007
         * hash port wins the implementation chain. */
3008
        Sha256_SetTransform();
3009
    #endif
3010
    #if defined(WOLFSSL_PPC64_ASM) && defined(WOLFSSL_PPC64_ASM_CRYPTO)
3011
        /* SHA-224 shares the SHA-256 transform; select the base/vector-crypto
3012
         * implementation at run time (sets sha256_use_crypto). */
3013
        Sha256_SetTransform();
3014
    #endif
3015
3.93k
    #ifdef WOLFSSL_HASH_FLAGS
3016
3.93k
        sha224->flags = 0;
3017
3.93k
    #endif
3018
    #ifdef WOLFSSL_HASH_KEEP
3019
        sha224->msg  = NULL;
3020
        sha224->len  = 0;
3021
        sha224->used = 0;
3022
    #endif
3023
3024
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
3025
       (!defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256) || \
3026
        !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224))
3027
        /* not to be confused with SHAS512_224 */
3028
        ret = esp_sha_init(&(sha224->ctx), WC_HASH_TYPE_SHA224);
3029
    #endif
3030
3031
3.93k
        return ret;
3032
3.93k
    }
3033
3034
#if !defined(WOLFSSL_HASH_KEEP)
3035
0
int wc_Sha224Reset(wc_Sha224* sha224) {
3036
0
    if (sha224 == NULL)
3037
0
        return BAD_FUNC_ARG;
3038
0
#ifdef WOLF_CRYPTO_CB
3039
    /* A device may hang state off devCtx that InitSha224() cannot restart.
3040
     * Free and re-init so the callback gets its teardown and setup. */
3041
0
    #ifndef WOLF_CRYPTO_CB_FIND
3042
0
    if (sha224->devId != INVALID_DEVID)
3043
0
    #endif
3044
0
    {
3045
0
        void* heap = sha224->heap;
3046
0
        int devId = sha224->devId;
3047
0
        wc_Sha224Free(sha224);
3048
0
        return wc_InitSha224_ex(sha224, heap, devId);
3049
0
    }
3050
0
#endif
3051
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA224) && \
3052
    defined(HAVE_INTEL_QA)
3053
    /* QAT caches updates in asyncDev, which InitSha224() cannot discard. */
3054
    {
3055
        int ret = IntelQaSymHashReset(&sha224->asyncDev);
3056
        if (ret != 0)
3057
            return ret;
3058
    }
3059
#endif
3060
0
    return InitSha224(sha224);
3061
0
}
3062
#define WC_SHA224RESET_DEFINED
3063
#endif /* !WOLFSSL_HASH_KEEP */
3064
3065
#endif
3066
3067
#ifdef NEED_SOFT_SHA224
3068
    int wc_InitSha224_ex(wc_Sha224* sha224, void* heap, int devId)
3069
1.34k
    {
3070
1.34k
        int ret = 0;
3071
3072
1.34k
        if (sha224 == NULL)
3073
0
            return BAD_FUNC_ARG;
3074
1.34k
    #ifdef WC_CTX_IS_ALIGNED
3075
1.34k
        if (!WC_CTX_IS_ALIGNED(sha224, wc_Sha224))
3076
0
            return BAD_ALIGN_E;
3077
1.34k
    #endif
3078
3079
1.34k
        WC_SILABS_CLEAR_HASH_CTX(sha224);
3080
1.34k
        sha224->heap = heap;
3081
    #ifdef WOLFSSL_SMALL_STACK_CACHE
3082
        sha224->W = NULL;
3083
    #endif
3084
1.34k
    #ifdef WOLF_CRYPTO_CB
3085
1.34k
        sha224->devId = devId;
3086
1.34k
        sha224->devCtx = NULL;
3087
1.34k
    #endif
3088
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW)
3089
        #if defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224)
3090
        /* We know this is a fresh, uninitialized item, so set to INIT */
3091
        if (sha224->ctx.mode != ESP32_SHA_SW) {
3092
            ESP_LOGV(TAG, "Set sha224 ctx mode init to ESP32_SHA_SW. "
3093
                          "Prior value: %d", sha224->ctx.mode);
3094
        }
3095
        /* no sha224 HW support is available, set to SW */
3096
            sha224->ctx.mode = ESP32_SHA_SW;
3097
        #else
3098
            /* We know this is a fresh, uninitialized item, so set to INIT */
3099
            sha224->ctx.mode = ESP32_SHA_INIT;
3100
        #endif
3101
    #endif
3102
3103
1.34k
        ret = InitSha224(sha224);
3104
1.34k
        if (ret != 0) {
3105
0
            return ret;
3106
0
        }
3107
3108
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA224)
3109
        ret = wolfAsync_DevCtxInit(&sha224->asyncDev,
3110
                            WOLFSSL_ASYNC_MARKER_SHA224, sha224->heap, devId);
3111
    #else
3112
1.34k
        (void)devId;
3113
1.34k
    #endif /* WOLFSSL_ASYNC_CRYPT */
3114
#ifdef WOLFSSL_IMXRT1170_CAAM
3115
     ret = wc_CAAM_HashInit(&sha224->hndl, &sha224->ctx, WC_HASH_TYPE_SHA224);
3116
#endif
3117
3118
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
3119
       (!defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256) || \
3120
        !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224))
3121
        if (sha224->ctx.mode != ESP32_SHA_INIT) {
3122
            ESP_LOGV("SHA224", "Set ctx mode from prior value: "
3123
                               "%d", sha224->ctx.mode);
3124
        }
3125
        /* We know this is a fresh, uninitialized item, so set to INIT */
3126
        sha224->ctx.mode = ESP32_SHA_INIT;
3127
    #endif
3128
3129
1.34k
        return ret;
3130
1.34k
    }
3131
3132
    int wc_Sha224Update(wc_Sha224* sha224, const byte* data, word32 len)
3133
5.65k
    {
3134
5.65k
        int ret;
3135
3136
5.65k
        if (sha224 == NULL) {
3137
0
            return BAD_FUNC_ARG;
3138
0
        }
3139
5.65k
        if (len == 0) {
3140
            /* valid, but do nothing */
3141
10
            return 0;
3142
10
        }
3143
5.64k
        if (data == NULL) {
3144
0
            return BAD_FUNC_ARG;
3145
0
        }
3146
5.64k
    #ifdef WOLF_CRYPTO_CB
3147
5.64k
        #ifndef WOLF_CRYPTO_CB_FIND
3148
5.64k
        if (sha224->devId != INVALID_DEVID)
3149
149
        #endif
3150
149
        {
3151
149
            ret = wc_CryptoCb_Sha224Hash(sha224, data, len, NULL);
3152
149
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3153
0
                return ret;
3154
            /* fall-through when unavailable */
3155
149
        }
3156
5.64k
    #endif
3157
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA224)
3158
        if (sha224->asyncDev.marker == WOLFSSL_ASYNC_MARKER_SHA224) {
3159
        #if defined(HAVE_INTEL_QA)
3160
            return IntelQaSymSha224(&sha224->asyncDev, NULL, data, len);
3161
        #endif
3162
        }
3163
    #endif /* WOLFSSL_ASYNC_CRYPT */
3164
3165
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
3166
       (defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256) || \
3167
        defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224))
3168
        sha224->ctx.mode = ESP32_SHA_SW; /* no SHA224 HW, so always SW */
3169
    #endif
3170
3171
5.64k
        ret = Sha256Update((wc_Sha256*)sha224, data, len);
3172
3173
5.64k
        return ret;
3174
5.64k
    }
3175
3176
    int wc_Sha224Final(wc_Sha224* sha224, byte* hash)
3177
2.58k
    {
3178
2.58k
        int ret;
3179
3180
2.58k
        if (sha224 == NULL || hash == NULL) {
3181
0
            return BAD_FUNC_ARG;
3182
0
        }
3183
2.58k
    #ifdef WOLF_CRYPTO_CB
3184
2.58k
        #ifndef WOLF_CRYPTO_CB_FIND
3185
2.58k
        if (sha224->devId != INVALID_DEVID)
3186
67
        #endif
3187
67
        {
3188
67
            ret = wc_CryptoCb_Sha224Hash(sha224, NULL, 0, hash);
3189
67
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3190
0
                return ret;
3191
            /* fall-through when unavailable */
3192
67
        }
3193
2.58k
    #endif
3194
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA224)
3195
        if (sha224->asyncDev.marker == WOLFSSL_ASYNC_MARKER_SHA224) {
3196
        #if defined(HAVE_INTEL_QA)
3197
            return IntelQaSymSha224(&sha224->asyncDev, hash, NULL,
3198
                                            WC_SHA224_DIGEST_SIZE);
3199
        #endif
3200
        }
3201
    #endif /* WOLFSSL_ASYNC_CRYPT */
3202
3203
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) &&      \
3204
       ( !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256) || \
3205
         !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224) )
3206
3207
        /* nothing enabled here for RISC-V C2/C3/C6 success */
3208
    #endif
3209
3210
2.58k
        ret = Sha256Final((wc_Sha256*)sha224);
3211
2.58k
        if (ret != 0)
3212
0
            return ret;
3213
3214
    #if defined(WOLFSSL_WIDE_BYTE)
3215
        /* CHAR_BIT != 8: store digest words as big-endian octets. */
3216
        BytesFromWordsBE32(hash, sha224->digest, WC_SHA224_DIGEST_SIZE);
3217
    #else
3218
2.58k
    #if defined(LITTLE_ENDIAN_ORDER)
3219
2.58k
        if (SHA256_REV_BYTES(&sha224->ctx)) {
3220
2.58k
            ByteReverseWords(sha224->digest,
3221
2.58k
                             sha224->digest,
3222
2.58k
                             WC_SHA224_DIGEST_SIZE);
3223
2.58k
        }
3224
2.58k
    #endif
3225
2.58k
        XMEMCPY(hash, sha224->digest, WC_SHA224_DIGEST_SIZE);
3226
2.58k
    #endif
3227
3228
2.58k
        return InitSha224(sha224);  /* reset state */
3229
2.58k
    }
3230
#endif /* end of SHA224 software implementation */
3231
3232
#ifdef WOLF_CRYPTO_CB_ONLY_SHA256
3233
3234
    int wc_Sha224Update(wc_Sha224* sha224, const byte* data, word32 len)
3235
    {
3236
        if (sha224 == NULL)
3237
            return BAD_FUNC_ARG;
3238
        if (data == NULL && len == 0)
3239
            return 0;
3240
        if (data == NULL)
3241
            return BAD_FUNC_ARG;
3242
3243
        #ifndef WOLF_CRYPTO_CB_FIND
3244
        if (sha224->devId != INVALID_DEVID)
3245
        #endif
3246
        {
3247
            int ret = wc_CryptoCb_Sha224Hash(sha224, data, len, NULL);
3248
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3249
                return ret;
3250
        }
3251
3252
        return NO_VALID_DEVID;
3253
    }
3254
3255
    int wc_Sha224Final(wc_Sha224* sha224, byte* hash)
3256
    {
3257
        int ret;
3258
3259
        if (sha224 == NULL || hash == NULL)
3260
            return BAD_FUNC_ARG;
3261
3262
        #ifndef WOLF_CRYPTO_CB_FIND
3263
        if (sha224->devId != INVALID_DEVID)
3264
        #endif
3265
        {
3266
            ret = wc_CryptoCb_Sha224Hash(sha224, NULL, 0, hash);
3267
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3268
                return ret;
3269
        }
3270
3271
        return NO_VALID_DEVID;
3272
    }
3273
3274
#endif /* WOLF_CRYPTO_CB_ONLY_SHA256 */
3275
3276
    int wc_InitSha224(wc_Sha224* sha224)
3277
67
    {
3278
67
        int devId = INVALID_DEVID;
3279
3280
67
    #ifdef WOLF_CRYPTO_CB
3281
67
        devId = wc_CryptoCb_DefaultDevID();
3282
67
    #endif
3283
67
        return wc_InitSha224_ex(sha224, NULL, devId);
3284
67
    }
3285
3286
#if !defined(WOLFSSL_HAVE_PSA) || defined(WOLFSSL_PSA_NO_HASH)
3287
    /* implemented in wolfcrypt/src/port/psa/psa_hash.c */
3288
3289
    void wc_Sha224Free(wc_Sha224* sha224)
3290
1.51k
    {
3291
#if defined(WOLF_CRYPTO_CB) && defined(WOLF_CRYPTO_CB_FREE)
3292
        int ret = 0;
3293
#endif
3294
3295
1.51k
        if (sha224 == NULL)
3296
0
            return;
3297
1.51k
    #ifdef WC_CTX_IS_ALIGNED
3298
1.51k
        if (!WC_CTX_IS_ALIGNED(sha224, wc_Sha224)) {
3299
0
            ForceZero(sha224, sizeof(*sha224));
3300
0
            return;
3301
0
        }
3302
1.51k
    #endif
3303
3304
#if defined(WOLF_CRYPTO_CB) && defined(WOLF_CRYPTO_CB_FREE)
3305
    #ifndef WOLF_CRYPTO_CB_FIND
3306
        if (sha224->devId != INVALID_DEVID)
3307
    #endif
3308
        {
3309
            ret = wc_CryptoCb_Free(sha224->devId, WC_ALGO_TYPE_HASH,
3310
                             WC_HASH_TYPE_SHA224, 0, (void*)sha224);
3311
            /* If they want the standard free, they can call it themselves */
3312
            /* via their callback setting devId to INVALID_DEVID */
3313
            /* otherwise assume the callback handled it */
3314
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3315
                return;
3316
            /* fall-through when unavailable */
3317
        }
3318
3319
        /* silence compiler warning */
3320
        (void)ret;
3321
3322
#endif /* WOLF_CRYPTO_CB && WOLF_CRYPTO_CB_FREE */
3323
3324
#ifdef WOLFSSL_SMALL_STACK_CACHE
3325
        if (sha224->W != NULL) {
3326
            ForceZero(sha224->W, sizeof(Sha256TScratch));
3327
            XFREE(sha224->W, sha224->heap, DYNAMIC_TYPE_DIGEST);
3328
            sha224->W = NULL;
3329
        }
3330
#endif
3331
3332
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA224)
3333
        wolfAsync_DevCtxFree(&sha224->asyncDev, WOLFSSL_ASYNC_MARKER_SHA224);
3334
    #endif /* WOLFSSL_ASYNC_CRYPT */
3335
3336
    #ifdef WOLFSSL_PIC32MZ_HASH
3337
        wc_Sha256Pic32Free(sha224);
3338
    #endif
3339
    #if defined(WOLFSSL_KCAPI_HASH)
3340
        KcapiHashFree(&sha224->kcapi);
3341
    #endif
3342
    #if defined(WOLFSSL_RENESAS_RX64_HASH)
3343
        if (sha224->msg != NULL) {
3344
            ForceZero(sha224->msg, sha224->len);
3345
            XFREE(sha224->msg, sha224->heap, DYNAMIC_TYPE_TMP_BUFFER);
3346
            sha224->msg = NULL;
3347
        }
3348
    #endif
3349
    #if defined(PSOC6_HASH_SHA2)
3350
        wc_Psoc6_Sha_Free();
3351
    #endif
3352
1.51k
        ForceZero(sha224, sizeof(*sha224));
3353
1.51k
    }
3354
#endif /* !defined(WOLFSSL_HAVE_PSA) || defined(WOLFSSL_PSA_NO_HASH)  */
3355
#endif /*  WOLFSSL_SHA224 */
3356
3357
3358
int wc_InitSha256(wc_Sha256* sha256)
3359
77
{
3360
77
    int devId = INVALID_DEVID;
3361
3362
77
#ifdef WOLF_CRYPTO_CB
3363
77
    devId = wc_CryptoCb_DefaultDevID();
3364
77
#endif
3365
77
    return wc_InitSha256_ex(sha256, NULL, devId);
3366
77
}
3367
3368
#if !defined(WOLFSSL_HAVE_PSA) || defined(WOLFSSL_PSA_NO_HASH)
3369
    /* implemented in wolfcrypt/src/port/psa/psa_hash.c */
3370
3371
void wc_Sha256Free(wc_Sha256* sha256)
3372
138k
{
3373
3374
#if defined(WOLF_CRYPTO_CB) && defined(WOLF_CRYPTO_CB_FREE)
3375
    int ret = 0;
3376
#endif
3377
3378
138k
    if (sha256 == NULL)
3379
0
        return;
3380
138k
#ifdef WC_CTX_IS_ALIGNED
3381
138k
    if (!WC_CTX_IS_ALIGNED(sha256, wc_Sha256)) {
3382
0
        ForceZero(sha256, sizeof(*sha256));
3383
0
        return;
3384
0
    }
3385
138k
#endif
3386
3387
#if defined(WOLF_CRYPTO_CB) && defined(WOLF_CRYPTO_CB_FREE)
3388
    #ifndef WOLF_CRYPTO_CB_FIND
3389
    if (sha256->devId != INVALID_DEVID)
3390
    #endif
3391
    {
3392
        ret = wc_CryptoCb_Free(sha256->devId, WC_ALGO_TYPE_HASH,
3393
                         WC_HASH_TYPE_SHA256, 0, (void*)sha256);
3394
        /* If they want the standard free, they can call it themselves */
3395
        /* via their callback setting devId to INVALID_DEVID */
3396
        /* otherwise assume the callback handled it */
3397
        if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3398
            return;
3399
        /* fall-through when unavailable */
3400
    }
3401
3402
    /* silence compiler warning */
3403
    (void)ret;
3404
3405
#endif /* WOLF_CRYPTO_CB && WOLF_CRYPTO_CB_FREE */
3406
3407
#if defined(WOLFSSL_ESP32) && \
3408
    !defined(NO_WOLFSSL_ESP32_CRYPT_HASH) && \
3409
    !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
3410
    esp_sha_release_unfinished_lock(&sha256->ctx);
3411
#endif
3412
3413
#ifdef WOLFSSL_SMALL_STACK_CACHE
3414
    if (sha256->W != NULL) {
3415
        ForceZero(sha256->W, sizeof(Sha256TScratch));
3416
        XFREE(sha256->W, sha256->heap, DYNAMIC_TYPE_DIGEST);
3417
        sha256->W = NULL;
3418
    }
3419
#endif
3420
3421
3422
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256)
3423
    wolfAsync_DevCtxFree(&sha256->asyncDev, WOLFSSL_ASYNC_MARKER_SHA256);
3424
#endif /* WOLFSSL_ASYNC_CRYPT */
3425
#ifdef WOLFSSL_PIC32MZ_HASH
3426
    wc_Sha256Pic32Free(sha256);
3427
#endif
3428
#if defined(WOLFSSL_AFALG_HASH)
3429
    if (sha256->alFd > 0) {
3430
        close(sha256->alFd);
3431
        sha256->alFd = -1; /* avoid possible double close on socket */
3432
    }
3433
    if (sha256->rdFd > 0) {
3434
        close(sha256->rdFd);
3435
        sha256->rdFd = -1; /* avoid possible double close on socket */
3436
    }
3437
#endif /* WOLFSSL_AFALG_HASH */
3438
#ifdef WOLFSSL_DEVCRYPTO_HASH
3439
    wc_DevCryptoFree(&sha256->ctx);
3440
#endif /* WOLFSSL_DEVCRYPTO */
3441
#if (defined(WOLFSSL_AFALG_HASH) && defined(WOLFSSL_AFALG_HASH_KEEP)) || \
3442
    (defined(WOLFSSL_DEVCRYPTO_HASH) && defined(WOLFSSL_DEVCRYPTO_HASH_KEEP)) || \
3443
    ((defined(WOLFSSL_RENESAS_TSIP_TLS) || \
3444
      defined(WOLFSSL_RENESAS_TSIP_CRYPTONLY)) && \
3445
    !defined(NO_WOLFSSL_RENESAS_TSIP_CRYPT_HASH)) || \
3446
    ((defined(WOLFSSL_RENESAS_SCEPROTECT) || \
3447
    (defined(WOLFSSL_RENESAS_RSIP) && (WOLFSSL_RENESAS_RZFSP_VER >= 220))) && \
3448
    !defined(NO_WOLFSSL_RENESAS_FSPSM_HASH)) || \
3449
    defined(WOLFSSL_RENESAS_RX64_HASH) || \
3450
    defined(WOLFSSL_HASH_KEEP)
3451
3452
    if (sha256->msg != NULL) {
3453
        ForceZero(sha256->msg, sha256->len);
3454
        XFREE(sha256->msg, sha256->heap, DYNAMIC_TYPE_TMP_BUFFER);
3455
        sha256->msg = NULL;
3456
    }
3457
#endif
3458
#if defined(WOLFSSL_SE050) && defined(WOLFSSL_SE050_HASH)
3459
    se050_hash_free(&sha256->se050Ctx);
3460
#endif
3461
#if defined(WOLFSSL_KCAPI_HASH)
3462
    KcapiHashFree(&sha256->kcapi);
3463
#endif
3464
#ifdef WOLFSSL_IMXRT_DCP
3465
    DCPSha256Free(sha256);
3466
#endif
3467
#ifdef WOLFSSL_MAXQ10XX_CRYPTO
3468
    wc_MAXQ10XX_Sha256Free(sha256);
3469
#endif
3470
3471
#ifdef HAVE_ARIA
3472
    if (sha256->hSession != NULL) {
3473
        MC_CloseSession(sha256->hSession);
3474
        sha256->hSession = NULL;
3475
    }
3476
#endif
3477
3478
/* Espressif embedded hardware acceleration specific: */
3479
#if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
3480
   !defined(NO_WOLFSSL_ESP32_CRYPT_HASH) && \
3481
   !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
3482
    if (sha256->ctx.lockDepth > 0) {
3483
        /* probably due to unclean shutdown, error, or other problem.
3484
         *
3485
         * if you find yourself here, code needs to be cleaned up to
3486
         * properly release hardware. this init is only for handling
3487
         * the unexpected. by the time free is called, the hardware
3488
         * should have already been released (lockDepth = 0)
3489
         */
3490
        (void)InitSha256(sha256); /* unlock mutex, set mode to ESP32_SHA_INIT */
3491
        ESP_LOGV(TAG, "Alert: hardware unlock needed in wc_Sha256Free.");
3492
    }
3493
    else {
3494
        ESP_LOGV(TAG, "Hardware unlock not needed in wc_Sha256Free.");
3495
    }
3496
#endif
3497
3498
#if defined(PSOC6_HASH_SHA2)
3499
    wc_Psoc6_Sha_Free();
3500
#endif
3501
3502
138k
    ForceZero(sha256, sizeof(*sha256));
3503
138k
} /* wc_Sha256Free */
3504
3505
#endif /* !defined(WOLFSSL_HAVE_PSA) || defined(WOLFSSL_PSA_NO_HASH) */
3506
#ifdef WOLFSSL_HASH_KEEP
3507
/* Some hardware have issues with update, this function stores the data to be
3508
 * hashed into an array. Once ready, the Final operation is called on all of the
3509
 * data to be hashed at once.
3510
 * returns 0 on success
3511
 */
3512
int wc_Sha256_Grow(wc_Sha256* sha256, const byte* in, int inSz)
3513
{
3514
    return _wc_Hash_Grow(&(sha256->msg), &(sha256->used), &(sha256->len), in,
3515
                        inSz, sha256->heap);
3516
}
3517
#ifdef WOLFSSL_SHA224
3518
int wc_Sha224_Grow(wc_Sha224* sha224, const byte* in, int inSz)
3519
{
3520
    return _wc_Hash_Grow(&(sha224->msg), &(sha224->used), &(sha224->len), in,
3521
                        inSz, sha224->heap);
3522
}
3523
#endif /* WOLFSSL_SHA224 */
3524
#endif /* WOLFSSL_HASH_KEEP */
3525
3526
#endif /* !WOLFSSL_TI_HASH */
3527
3528
/* Fallback implementations of the Reset functions, for all configurations other
3529
 * than plain software.  Continues with the established heap and devId.
3530
 */
3531
3532
#ifndef WC_SHA256RESET_DEFINED
3533
3534
int wc_Sha256Reset(wc_Sha256* sha256) {
3535
    void *heap;
3536
    int devId;
3537
3538
    if (sha256 == NULL)
3539
        return BAD_FUNC_ARG;
3540
3541
    heap = sha256->heap;
3542
#ifdef WOLF_CRYPTO_CB
3543
    devId = sha256->devId;
3544
#else
3545
    devId = INVALID_DEVID;
3546
#endif
3547
3548
    wc_Sha256Free(sha256);
3549
    return wc_InitSha256_ex(sha256, heap, devId);
3550
}
3551
#define WC_SHA256RESET_DEFINED
3552
#endif
3553
3554
#if defined(WOLFSSL_SHA224) && !defined(WC_SHA224RESET_DEFINED)
3555
int wc_Sha224Reset(wc_Sha224* sha224) {
3556
    void *heap;
3557
    int devId;
3558
3559
    if (sha224 == NULL)
3560
        return BAD_FUNC_ARG;
3561
3562
    heap = sha224->heap;
3563
#ifdef WOLF_CRYPTO_CB
3564
    devId = sha224->devId;
3565
#else
3566
    devId = INVALID_DEVID;
3567
#endif
3568
3569
    wc_Sha224Free(sha224);
3570
    return wc_InitSha224_ex(sha224, heap, devId);
3571
}
3572
#define WC_SHA224RESET_DEFINED
3573
#endif /* WOLFSSL_SHA224 && !WC_SHA224RESET_DEFINED */
3574
3575
#ifndef WOLFSSL_TI_HASH
3576
#if !defined(WOLFSSL_RENESAS_RX64_HASH) && \
3577
    (!defined(WOLFSSL_RENESAS_RSIP) || \
3578
      defined(NO_WOLFSSL_RENESAS_FSPSM_HASH))
3579
#ifdef WOLFSSL_SHA224
3580
3581
#if defined(WOLFSSL_KCAPI_HASH) && !defined(WOLFSSL_NO_KCAPI_SHA224)
3582
    /* implemented in wolfcrypt/src/port/kcapi/kcapi_hash.c */
3583
#elif defined(WOLFSSL_HAVE_PSA) && !defined(WOLFSSL_PSA_NO_HASH)
3584
    /* implemented in wolfcrypt/src/port/psa/psa_hash.c */
3585
3586
#elif defined(MAX3266X_SHA)
3587
    /* implemented in wolfcrypt/src/port/maxim/max3266x.c */
3588
3589
#else
3590
3591
    int wc_Sha224GetHash(wc_Sha224* sha224, byte* hash)
3592
0
    {
3593
0
        int ret;
3594
0
        WC_DECLARE_VAR(tmpSha224, wc_Sha224, 1, 0);
3595
3596
0
        if (sha224 == NULL || hash == NULL) {
3597
0
            return BAD_FUNC_ARG;
3598
0
        }
3599
3600
0
        WC_CALLOC_VAR_EX(tmpSha224, wc_Sha224, 1, NULL,
3601
0
            DYNAMIC_TYPE_TMP_BUFFER, return MEMORY_E);
3602
    #ifdef WOLFSSL_CHECK_MEM_ZERO
3603
        wc_MemZero_Add("wc_Sha224GetHash tmpSha224", tmpSha224,
3604
            sizeof(*tmpSha224));
3605
    #endif
3606
3607
0
        ret = wc_Sha224Copy(sha224, tmpSha224);
3608
0
        if (ret == 0) {
3609
0
            ret = wc_Sha224Final(tmpSha224, hash);
3610
0
            wc_Sha224Free(tmpSha224);
3611
0
        }
3612
3613
0
        ForceZero(tmpSha224, sizeof(*tmpSha224));
3614
    #if defined(WOLFSSL_CHECK_MEM_ZERO) && !defined(WOLFSSL_SMALL_STACK)
3615
        wc_MemZero_Check(tmpSha224, sizeof(*tmpSha224));
3616
    #endif
3617
3618
0
        WC_FREE_VAR_EX(tmpSha224, NULL, DYNAMIC_TYPE_TMP_BUFFER);
3619
0
        return ret;
3620
0
    }
3621
3622
    int wc_Sha224Copy(wc_Sha224* src, wc_Sha224* dst)
3623
48
    {
3624
48
        int ret = 0; /* assume success unless proven otherwise */
3625
3626
48
        if (src == NULL || dst == NULL || src == dst) {
3627
0
            return BAD_FUNC_ARG;
3628
0
        }
3629
48
    #ifdef WC_CTX_IS_ALIGNED
3630
48
        if (!WC_CTX_IS_ALIGNED(dst, wc_Sha224)) {
3631
0
            return BAD_ALIGN_E;
3632
0
        }
3633
48
    #endif
3634
3635
#if defined(WOLF_CRYPTO_CB) && defined(WOLF_CRYPTO_CB_COPY)
3636
    #ifndef WOLF_CRYPTO_CB_FIND
3637
        if (src->devId != INVALID_DEVID)
3638
    #endif
3639
        {
3640
            /* Cast the source and destination to be void to keep the abstraction */
3641
            ret = wc_CryptoCb_Copy(src->devId, WC_ALGO_TYPE_HASH,
3642
                                   WC_HASH_TYPE_SHA224, (void*)src, (void*)dst);
3643
            if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3644
                return ret;
3645
            /* fall-through when unavailable */
3646
        }
3647
        ret = 0; /* Reset ret to 0 to avoid returning the callback error code */
3648
#endif /* WOLF_CRYPTO_CB && WOLF_CRYPTO_CB_COPY */
3649
3650
        /* Free dst resources before copy to prevent memory leaks (e.g., msg
3651
         * buffer, W cache, hardware contexts). XMEMCPY overwrites dst. */
3652
48
        wc_Sha224Free(dst);
3653
48
        XMEMCPY(dst, src, sizeof(wc_Sha224));
3654
3655
    #ifdef WOLFSSL_SMALL_STACK_CACHE
3656
        dst->W = (word32*)XMALLOC(WC_SHA256_TSCRATCH_SIZE,
3657
                                  dst->heap, DYNAMIC_TYPE_DIGEST);
3658
        if (dst->W == NULL) {
3659
            ForceZero(dst, sizeof(wc_Sha224));
3660
            return MEMORY_E;
3661
        }
3662
    #endif
3663
3664
    #if defined(WOLFSSL_SILABS_SE_TYPES) && defined(WOLFSSL_SILABS_SE_ACCEL_3)
3665
        dst->silabsCtx.hash_ctx.cmd_ctx = &dst->silabsCtx.cmd_ctx;
3666
        dst->silabsCtx.hash_ctx.hash_type_ctx = &dst->silabsCtx.hash_type_ctx;
3667
    #endif
3668
3669
    #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA224)
3670
        ret = wolfAsync_DevCopy(&src->asyncDev, &dst->asyncDev);
3671
    #endif
3672
3673
    #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
3674
       (!defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256) || \
3675
        !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224))
3676
        /* regardless of any other settings, there's no SHA-224 HW on ESP32 */
3677
        #ifndef CONFIG_IDF_TARGET_ESP32
3678
            ret = esp_sha224_ctx_copy(src, dst);
3679
        #endif
3680
    #endif
3681
3682
48
    #ifdef WOLFSSL_HASH_FLAGS
3683
48
        dst->flags |= WC_HASH_FLAG_ISCOPY;
3684
48
    #endif
3685
3686
    #if defined(WOLFSSL_HASH_KEEP)
3687
        if (src->msg != NULL) {
3688
            dst->msg = (byte*)XMALLOC(src->len, dst->heap,
3689
                                      DYNAMIC_TYPE_TMP_BUFFER);
3690
            if (dst->msg == NULL)
3691
                return MEMORY_E;
3692
            XMEMCPY(dst->msg, src->msg, src->len);
3693
        }
3694
    #endif
3695
3696
    #if defined(PSOC6_HASH_SHA2)
3697
        wc_Psoc6_Sha1_Sha2_Init(dst, WC_PSOC6_SHA224, 0);
3698
    #endif
3699
48
        return ret;
3700
48
    }
3701
3702
#endif /* WOLFSSL_KCAPI_HASH && !WOLFSSL_NO_KCAPI_SHA224 */
3703
3704
#ifdef WOLFSSL_HASH_FLAGS
3705
    int wc_Sha224SetFlags(wc_Sha224* sha224, word32 flags)
3706
0
    {
3707
0
        if (sha224) {
3708
0
            sha224->flags = flags;
3709
0
        }
3710
0
        return 0;
3711
0
    }
3712
    int wc_Sha224GetFlags(wc_Sha224* sha224, word32* flags)
3713
0
    {
3714
0
        if (sha224 && flags) {
3715
0
            *flags = sha224->flags;
3716
0
        }
3717
0
        return 0;
3718
0
    }
3719
#endif
3720
3721
#endif /* WOLFSSL_SHA224 */
3722
#endif /* WOLFSSL_RENESAS_RX64_HASH */
3723
3724
#ifdef WOLFSSL_AFALG_HASH
3725
    /* implemented in wolfcrypt/src/port/af_alg/afalg_hash.c */
3726
3727
#elif defined(WOLFSSL_DEVCRYPTO_HASH)
3728
    /* implemented in wolfcrypt/src/port/devcrypto/devcrypt_hash.c */
3729
3730
#elif (defined(WOLFSSL_RENESAS_TSIP_TLS) || \
3731
       defined(WOLFSSL_RENESAS_TSIP_CRYPTONLY)) && \
3732
    !defined(NO_WOLFSSL_RENESAS_TSIP_CRYPT_HASH)
3733
3734
    /* implemented in wolfcrypt/src/port/Renesas/renesas_tsip_sha.c */
3735
3736
#elif (defined(WOLFSSL_RENESAS_SCEPROTECT) || defined(WOLFSSL_RENESAS_RSIP))\
3737
     && !defined(NO_WOLFSSL_RENESAS_FSPSM_HASH)
3738
3739
    /* implemented in wolfcrypt/src/port/Renesas/renesas_fspsm_sha.c */
3740
#elif defined(WOLFSSL_IMXRT_DCP)
3741
    /* implemented in wolfcrypt/src/port/nxp/dcp_port.c */
3742
#elif defined(WOLFSSL_KCAPI_HASH)
3743
    /* implemented in wolfcrypt/src/port/kcapi/kcapi_hash.c */
3744
3745
#elif defined(WOLFSSL_HAVE_PSA) && !defined(WOLFSSL_PSA_NO_HASH)
3746
    /* implemented in wolfcrypt/src/port/psa/psa_hash.c */
3747
#elif defined(WOLFSSL_RENESAS_RX64_HASH)
3748
    /* implemented in wolfcrypt/src/port/Renesas/renesas_rx64_hw_sha.c */
3749
#elif defined(MAX3266X_SHA)
3750
    /* Implemented in wolfcrypt/src/port/maxim/max3266x.c */
3751
#else
3752
3753
int wc_Sha256GetHash(wc_Sha256* sha256, byte* hash)
3754
5.30k
{
3755
5.30k
    int ret;
3756
5.30k
    WC_DECLARE_VAR(tmpSha256, wc_Sha256, 1, 0);
3757
3758
5.30k
    if (sha256 == NULL || hash == NULL) {
3759
0
        return BAD_FUNC_ARG;
3760
0
    }
3761
3762
5.30k
    WC_CALLOC_VAR_EX(tmpSha256, wc_Sha256, 1, NULL, DYNAMIC_TYPE_TMP_BUFFER,
3763
5.30k
        return MEMORY_E);
3764
#ifdef WOLFSSL_CHECK_MEM_ZERO
3765
    wc_MemZero_Add("wc_Sha256GetHash tmpSha256", tmpSha256,
3766
        sizeof(*tmpSha256));
3767
#endif
3768
3769
5.30k
    ret = wc_Sha256Copy(sha256, tmpSha256);
3770
5.30k
    if (ret == 0) {
3771
5.30k
        ret = wc_Sha256Final(tmpSha256, hash);
3772
5.30k
        wc_Sha256Free(tmpSha256);
3773
5.30k
    }
3774
3775
3776
5.30k
    ForceZero(tmpSha256, sizeof(*tmpSha256));
3777
#if defined(WOLFSSL_CHECK_MEM_ZERO) && !defined(WOLFSSL_SMALL_STACK)
3778
    wc_MemZero_Check(tmpSha256, sizeof(*tmpSha256));
3779
#endif
3780
3781
3782
5.30k
    WC_FREE_VAR_EX(tmpSha256, NULL, DYNAMIC_TYPE_TMP_BUFFER);
3783
3784
5.30k
    return ret;
3785
5.30k
}
3786
int wc_Sha256Copy(wc_Sha256* src, wc_Sha256* dst)
3787
5.34k
{
3788
5.34k
    int ret = 0;
3789
3790
5.34k
    if (src == NULL || dst == NULL || src == dst) {
3791
0
        return BAD_FUNC_ARG;
3792
0
    }
3793
5.34k
#ifdef WC_CTX_IS_ALIGNED
3794
5.34k
    if (!WC_CTX_IS_ALIGNED(dst, wc_Sha256)) {
3795
0
        return BAD_ALIGN_E;
3796
0
    }
3797
5.34k
#endif
3798
3799
#if defined(WOLF_CRYPTO_CB) && defined(WOLF_CRYPTO_CB_COPY)
3800
    #ifndef WOLF_CRYPTO_CB_FIND
3801
    if (src->devId != INVALID_DEVID)
3802
    #endif
3803
    {
3804
        /* Cast the source and destination to be void to keep the abstraction */
3805
        ret = wc_CryptoCb_Copy(src->devId, WC_ALGO_TYPE_HASH,
3806
                               WC_HASH_TYPE_SHA256, (void*)src, (void*)dst);
3807
        if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE))
3808
            return ret;
3809
        /* fall-through when unavailable */
3810
    }
3811
    ret = 0; /* Reset ret to 0 to avoid returning the callback error code */
3812
#endif /* WOLF_CRYPTO_CB && WOLF_CRYPTO_CB_COPY */
3813
3814
    /* Free dst resources before copy to prevent memory leaks (e.g., msg
3815
     * buffer, W cache, hardware contexts). XMEMCPY overwrites dst. */
3816
5.34k
    wc_Sha256Free(dst);
3817
5.34k
    XMEMCPY(dst, src, sizeof(wc_Sha256));
3818
3819
#ifdef WOLFSSL_MAXQ10XX_CRYPTO
3820
    wc_MAXQ10XX_Sha256Copy(src);
3821
#endif
3822
3823
3824
#ifdef WOLFSSL_SMALL_STACK_CACHE
3825
    dst->W = (word32*)XMALLOC(WC_SHA256_TSCRATCH_SIZE,
3826
                              dst->heap, DYNAMIC_TYPE_DIGEST);
3827
    if (dst->W == NULL) {
3828
        ForceZero(dst, sizeof(wc_Sha256));
3829
        return MEMORY_E;
3830
    }
3831
#endif
3832
3833
#if defined(WOLFSSL_SILABS_SE_TYPES) && defined(WOLFSSL_SILABS_SE_ACCEL_3)
3834
    dst->silabsCtx.hash_ctx.cmd_ctx = &dst->silabsCtx.cmd_ctx;
3835
    dst->silabsCtx.hash_ctx.hash_type_ctx = &dst->silabsCtx.hash_type_ctx;
3836
#endif
3837
3838
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_SHA256)
3839
    ret = wolfAsync_DevCopy(&src->asyncDev, &dst->asyncDev);
3840
#endif
3841
3842
#ifdef WOLFSSL_PIC32MZ_HASH
3843
    ret = wc_Pic32HashCopy(&src->cache, &dst->cache, (byte*)src->buffer,
3844
        (byte*)dst->buffer, dst->heap);
3845
#endif
3846
3847
#if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) && \
3848
   !defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA256)
3849
    esp_sha256_ctx_copy(src, dst);
3850
#endif
3851
3852
#ifdef HAVE_ARIA
3853
    dst->hSession = NULL;
3854
    if((src->hSession != NULL) && (MC_CopySession(src->hSession, &(dst->hSession)) != MC_OK)) {
3855
        return MEMORY_E;
3856
    }
3857
#endif
3858
3859
#if defined(WOLFSSL_TI_AM64X_R5) && !defined(WOLFSSL_TI_AM64X_NO_SHA)
3860
    dst->devCtx = NULL;
3861
#endif
3862
3863
5.34k
#ifdef WOLFSSL_HASH_FLAGS
3864
5.34k
    dst->flags |= WC_HASH_FLAG_ISCOPY;
3865
5.34k
#endif
3866
3867
    /* The XMEMCPY(dst, src, sizeof(wc_Sha256)) above copies src->msg as a
3868
     * raw pointer value, aliasing dst->msg to the same heap block. For any
3869
     * backend that buffers the whole message in sha256->msg (see the
3870
     * matching condition in wc_Sha256Free() above), that block later gets
3871
     * freed once via src's own Final()/Free() call and a second time via
3872
     * dst's -- a double free that silently corrupts the heap a little more
3873
     * on every wc_Sha256Copy()+wc_Sha256Free(dst) pair, instead of crashing
3874
     * outright. Give dst its own independent copy so the two objects don't
3875
     * share ownership of the same allocation. */
3876
#if defined(WOLFSSL_HASH_KEEP) || \
3877
    (defined(WOLFSSL_AFALG_HASH) && defined(WOLFSSL_AFALG_HASH_KEEP)) || \
3878
    (defined(WOLFSSL_DEVCRYPTO_HASH) && defined(WOLFSSL_DEVCRYPTO_HASH_KEEP)) || \
3879
    ((defined(WOLFSSL_RENESAS_TSIP_TLS) || \
3880
      defined(WOLFSSL_RENESAS_TSIP_CRYPTONLY)) && \
3881
    !defined(NO_WOLFSSL_RENESAS_TSIP_CRYPT_HASH)) || \
3882
    ((defined(WOLFSSL_RENESAS_SCEPROTECT) || \
3883
    (defined(WOLFSSL_RENESAS_RSIP) && (WOLFSSL_RENESAS_RZFSP_VER >= 220))) && \
3884
    !defined(NO_WOLFSSL_RENESAS_FSPSM_HASH)) || \
3885
    defined(WOLFSSL_RENESAS_RX64_HASH)
3886
    if (src->msg != NULL) {
3887
        dst->msg = (byte*)XMALLOC(src->len, dst->heap, DYNAMIC_TYPE_TMP_BUFFER);
3888
        if (dst->msg == NULL)
3889
            return MEMORY_E;
3890
        XMEMCPY(dst->msg, src->msg, src->len);
3891
    }
3892
#endif
3893
3894
#if defined(PSOC6_HASH_SHA2)
3895
    if ((ret == 0) && (wc_Psoc6_Sha1_Sha2_Init(dst, WC_PSOC6_SHA256, 0) != 0))
3896
        ret = WC_HW_E;
3897
#endif
3898
3899
5.34k
    return ret;
3900
5.34k
}
3901
#endif
3902
3903
#ifdef WOLFSSL_HASH_FLAGS
3904
int wc_Sha256SetFlags(wc_Sha256* sha256, word32 flags)
3905
75.5k
{
3906
75.5k
    if (sha256) {
3907
75.5k
        sha256->flags = flags;
3908
75.5k
    }
3909
75.5k
    return 0;
3910
75.5k
}
3911
int wc_Sha256GetFlags(wc_Sha256* sha256, word32* flags)
3912
0
{
3913
0
    if (sha256 && flags) {
3914
0
        *flags = sha256->flags;
3915
0
    }
3916
0
    return 0;
3917
0
}
3918
#endif
3919
#endif /* !WOLFSSL_TI_HASH */
3920
3921
#endif /* NO_SHA256 */