Coverage Report

Created: 2026-02-14 07:18

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/wolfssl-openssl-api/src/ssl.c
Line
Count
Source
1
/* ssl.c
2
 *
3
 * Copyright (C) 2006-2025 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
#include <wolfssl/wolfcrypt/libwolfssl_sources.h>
23
24
#if defined(OPENSSL_EXTRA) && !defined(_WIN32) && !defined(_GNU_SOURCE)
25
    /* turn on GNU extensions for XISASCII */
26
    #define _GNU_SOURCE 1
27
#endif
28
29
#if !defined(WOLFCRYPT_ONLY) || defined(OPENSSL_EXTRA) || \
30
    defined(OPENSSL_EXTRA_X509_SMALL)
31
32
#include <wolfssl/internal.h>
33
#include <wolfssl/error-ssl.h>
34
#include <wolfssl/wolfcrypt/error-crypt.h>
35
#include <wolfssl/wolfcrypt/coding.h>
36
#include <wolfssl/wolfcrypt/kdf.h>
37
#ifdef NO_INLINE
38
    #include <wolfssl/wolfcrypt/misc.h>
39
#else
40
    #define WOLFSSL_MISC_INCLUDED
41
    #include <wolfcrypt/src/misc.c>
42
#endif
43
44
#ifdef HAVE_ERRNO_H
45
    #include <errno.h>
46
#endif
47
48
49
#if !defined(WOLFSSL_ALLOW_NO_SUITES) && !defined(WOLFCRYPT_ONLY)
50
    #if defined(NO_DH) && !defined(HAVE_ECC) && !defined(WOLFSSL_STATIC_RSA) \
51
                && !defined(WOLFSSL_STATIC_DH) && !defined(WOLFSSL_STATIC_PSK) \
52
                && !defined(HAVE_CURVE25519) && !defined(HAVE_CURVE448)
53
        #error "No cipher suites defined because DH disabled, ECC disabled, " \
54
               "and no static suites defined. Please see top of README"
55
    #endif
56
    #ifdef WOLFSSL_CERT_GEN
57
        /* need access to Cert struct for creating certificate */
58
        #include <wolfssl/wolfcrypt/asn_public.h>
59
    #endif
60
#endif
61
62
#if !defined(WOLFCRYPT_ONLY) && (defined(OPENSSL_EXTRA)     \
63
    || defined(OPENSSL_EXTRA_X509_SMALL)                    \
64
    || defined(HAVE_WEBSERVER) || defined(WOLFSSL_KEY_GEN))
65
    #include <wolfssl/openssl/evp.h>
66
    /* openssl headers end, wolfssl internal headers next */
67
#endif
68
69
#include <wolfssl/wolfcrypt/wc_encrypt.h>
70
71
#ifndef NO_RSA
72
    #include <wolfssl/wolfcrypt/rsa.h>
73
#endif
74
75
#ifdef OPENSSL_EXTRA
76
    /* openssl headers begin */
77
    #include <wolfssl/openssl/ssl.h>
78
    #include <wolfssl/openssl/aes.h>
79
#ifndef WOLFCRYPT_ONLY
80
    #include <wolfssl/openssl/hmac.h>
81
    #include <wolfssl/openssl/cmac.h>
82
#endif
83
    #include <wolfssl/openssl/crypto.h>
84
    #include <wolfssl/openssl/des.h>
85
    #include <wolfssl/openssl/bn.h>
86
    #include <wolfssl/openssl/buffer.h>
87
    #include <wolfssl/openssl/dh.h>
88
    #include <wolfssl/openssl/rsa.h>
89
    #include <wolfssl/openssl/fips_rand.h>
90
    #include <wolfssl/openssl/pem.h>
91
    #include <wolfssl/openssl/ec.h>
92
    #include <wolfssl/openssl/ec25519.h>
93
    #include <wolfssl/openssl/ed25519.h>
94
    #include <wolfssl/openssl/ec448.h>
95
    #include <wolfssl/openssl/ed448.h>
96
    #include <wolfssl/openssl/ecdsa.h>
97
    #include <wolfssl/openssl/ecdh.h>
98
    #include <wolfssl/openssl/err.h>
99
    #include <wolfssl/openssl/modes.h>
100
    #include <wolfssl/openssl/opensslv.h>
101
    #include <wolfssl/openssl/rc4.h>
102
    #include <wolfssl/openssl/stack.h>
103
    #include <wolfssl/openssl/x509_vfy.h>
104
    /* openssl headers end, wolfssl internal headers next */
105
    #include <wolfssl/wolfcrypt/hmac.h>
106
    #include <wolfssl/wolfcrypt/random.h>
107
    #include <wolfssl/wolfcrypt/des3.h>
108
    #include <wolfssl/wolfcrypt/ecc.h>
109
    #include <wolfssl/wolfcrypt/md4.h>
110
    #include <wolfssl/wolfcrypt/md5.h>
111
    #include <wolfssl/wolfcrypt/arc4.h>
112
    #include <wolfssl/wolfcrypt/curve25519.h>
113
    #include <wolfssl/wolfcrypt/ed25519.h>
114
    #include <wolfssl/wolfcrypt/curve448.h>
115
    #if defined(HAVE_FALCON)
116
        #include <wolfssl/wolfcrypt/falcon.h>
117
    #endif /* HAVE_FALCON */
118
    #if defined(HAVE_DILITHIUM)
119
        #include <wolfssl/wolfcrypt/dilithium.h>
120
    #endif /* HAVE_DILITHIUM */
121
    #if defined(HAVE_SPHINCS)
122
        #include <wolfssl/wolfcrypt/sphincs.h>
123
    #endif /* HAVE_SPHINCS */
124
    #if defined(OPENSSL_ALL) || defined(HAVE_STUNNEL)
125
        #ifdef HAVE_OCSP
126
            #include <wolfssl/openssl/ocsp.h>
127
        #endif
128
        #include <wolfssl/openssl/lhash.h>
129
        #include <wolfssl/openssl/txt_db.h>
130
    #endif /* WITH_STUNNEL */
131
    #if defined(WOLFSSL_SHA512) || defined(WOLFSSL_SHA384)
132
        #include <wolfssl/wolfcrypt/sha512.h>
133
    #endif
134
    #if defined(WOLFCRYPT_HAVE_SRP) && !defined(NO_SHA256) \
135
        && !defined(WC_NO_RNG)
136
        #include <wolfssl/wolfcrypt/srp.h>
137
    #endif
138
#endif
139
140
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
141
    #include <wolfssl/openssl/x509v3.h>
142
    int wolfssl_bn_get_value(WOLFSSL_BIGNUM* bn, mp_int* mpi);
143
    int wolfssl_bn_set_value(WOLFSSL_BIGNUM** bn, mp_int* mpi);
144
#endif
145
146
#if defined(WOLFSSL_QT)
147
    #include <wolfssl/wolfcrypt/sha.h>
148
#endif
149
150
#ifdef NO_ASN
151
    #include <wolfssl/wolfcrypt/dh.h>
152
#endif
153
#endif /* !WOLFCRYPT_ONLY || OPENSSL_EXTRA */
154
155
/*
156
 * OPENSSL_COMPATIBLE_DEFAULTS:
157
 *     Enable default behaviour that is compatible with OpenSSL. For example
158
 *     SSL_CTX by default doesn't verify the loaded certs. Enabling this
159
 *     should make porting to new projects easier.
160
 * WOLFSSL_CHECK_ALERT_ON_ERR:
161
 *     Check for alerts during the handshake in the event of an error.
162
 * NO_SESSION_CACHE_REF:
163
 *     wolfSSL_get_session on a client will return a reference to the internal
164
 *     ClientCache by default for backwards compatibility. This define will
165
 *     make wolfSSL_get_session return a reference to ssl->session. The returned
166
 *     pointer will be freed with the related WOLFSSL object.
167
 * SESSION_CACHE_DYNAMIC_MEM:
168
 *     Dynamically allocate sessions for the session cache from the heap, as
169
 *     opposed to the default which allocates from the stack.  Allocates
170
 *     memory only when a session is added to the cache, frees memory after the
171
 *     session is no longer being used.  Recommended for memory-constrained
172
 *     systems.
173
 * WOLFSSL_SYS_CA_CERTS
174
 *     Enables ability to load system CA certs from the OS via
175
 *     wolfSSL_CTX_load_system_CA_certs.
176
 */
177
178
#define WOLFSSL_SSL_MISC_INCLUDED
179
#include "src/ssl_misc.c"
180
181
#define WOLFSSL_EVP_INCLUDED
182
#include "wolfcrypt/src/evp.c"
183
184
/* Crypto code uses EVP APIs. */
185
#define WOLFSSL_SSL_CRYPTO_INCLUDED
186
#include "src/ssl_crypto.c"
187
188
#ifndef WOLFCRYPT_ONLY
189
#define WOLFSSL_SSL_CERTMAN_INCLUDED
190
#include "src/ssl_certman.c"
191
192
#define WOLFSSL_SSL_SESS_INCLUDED
193
#include "src/ssl_sess.c"
194
195
#define WOLFSSL_SSL_API_CERT_INCLUDED
196
#include "src/ssl_api_cert.c"
197
198
#define WOLFSSL_SSL_API_PK_INCLUDED
199
#include "src/ssl_api_pk.c"
200
#endif
201
202
#if (defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)) && \
203
    !defined(WOLFCRYPT_ONLY)
204
/* Convert shortname to NID.
205
 *
206
 * For OpenSSL compatibility.
207
 *
208
 * @param [in] sn  Short name of OID.
209
 * @return  NID corresponding to shortname on success.
210
 * @return  WC_NID_undef when not recognized.
211
 */
212
int wc_OBJ_sn2nid(const char *sn)
213
0
{
214
0
    const WOLFSSL_ObjectInfo *obj_info = wolfssl_object_info;
215
0
    size_t i;
216
0
    WOLFSSL_ENTER("wc_OBJ_sn2nid");
217
0
    for (i = 0; i < wolfssl_object_info_sz; i++, obj_info++) {
218
0
        if (XSTRCMP(sn, obj_info->sName) == 0)
219
0
            return obj_info->nid;
220
0
    }
221
0
    WOLFSSL_MSG("short name not found in table");
222
0
    return WC_NID_undef;
223
0
}
224
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
225
226
#ifndef WOLFCRYPT_ONLY
227
228
229
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
230
/* The system wide crypto-policy. Configured by wolfSSL_crypto_policy_enable.
231
 * */
232
static struct SystemCryptoPolicy crypto_policy;
233
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
234
235
#if !defined(NO_RSA) || !defined(NO_DH) || defined(HAVE_ECC) || \
236
    (defined(OPENSSL_EXTRA) && defined(WOLFSSL_KEY_GEN) && !defined(NO_DSA))
237
238
#define HAVE_GLOBAL_RNG /* consolidate flags for using globalRNG */
239
static WC_RNG globalRNG;
240
static volatile int initGlobalRNG = 0;
241
242
#if defined(OPENSSL_EXTRA) || !defined(WOLFSSL_MUTEX_INITIALIZER)
243
static WC_MAYBE_UNUSED wolfSSL_Mutex globalRNGMutex
244
    WOLFSSL_MUTEX_INITIALIZER_CLAUSE(globalRNGMutex);
245
#endif
246
#ifndef WOLFSSL_MUTEX_INITIALIZER
247
static int globalRNGMutex_valid = 0;
248
#endif
249
250
#if defined(OPENSSL_EXTRA) && defined(HAVE_HASHDRBG)
251
static WOLFSSL_DRBG_CTX* gDrbgDefCtx = NULL;
252
#endif
253
254
WC_RNG* wolfssl_get_global_rng(void)
255
564
{
256
564
    WC_RNG* ret = NULL;
257
258
564
    if (initGlobalRNG == 0)
259
545
        WOLFSSL_MSG("Global RNG no Init");
260
19
    else
261
19
        ret = &globalRNG;
262
263
564
    return ret;
264
564
}
265
266
/* Make a global RNG and return.
267
 *
268
 * @return  Global RNG on success.
269
 * @return  NULL on error.
270
 */
271
WC_RNG* wolfssl_make_global_rng(void)
272
0
{
273
0
    WC_RNG* ret;
274
275
0
#ifdef HAVE_GLOBAL_RNG
276
    /* Get the global random number generator instead. */
277
0
    ret = wolfssl_get_global_rng();
278
0
#ifdef OPENSSL_EXTRA
279
0
    if (ret == NULL) {
280
        /* Create a global random if possible. */
281
0
        (void)wolfSSL_RAND_Init();
282
0
        ret = wolfssl_get_global_rng();
283
0
    }
284
0
#endif
285
#else
286
    WOLFSSL_ERROR_MSG("Bad RNG Init");
287
    ret = NULL;
288
#endif
289
290
0
    return ret;
291
0
}
292
293
/* Too many defines to check explicitly - prototype it and always include
294
 * for RSA, DH, ECC and DSA for BN. */
295
WC_RNG* wolfssl_make_rng(WC_RNG* rng, int* local);
296
297
/* Make a random number generator or get global if possible.
298
 *
299
 * Global may not be available and NULL will be returned.
300
 *
301
 * @param [in, out] rng    Local random number generator.
302
 * @param [out]     local  Local random number generator returned.
303
 * @return  NULL on failure.
304
 * @return  A random number generator object.
305
 */
306
WC_RNG* wolfssl_make_rng(WC_RNG* rng, int* local)
307
599
{
308
599
    WC_RNG* ret = NULL;
309
599
#ifdef WOLFSSL_SMALL_STACK
310
599
    int freeRng = 0;
311
312
    /* Allocate RNG object . */
313
599
    if (rng == NULL) {
314
599
        rng = (WC_RNG*)XMALLOC(sizeof(WC_RNG), NULL, DYNAMIC_TYPE_RNG);
315
599
        freeRng = 1;
316
599
    }
317
599
#endif
318
319
599
    if (rng != NULL) {
320
599
        if (wc_InitRng(rng) == 0) {
321
599
            ret = rng;
322
599
            *local = 1;
323
599
        }
324
0
        else {
325
0
            WOLFSSL_MSG("Bad RNG Init");
326
0
#ifdef WOLFSSL_SMALL_STACK
327
0
            if (freeRng) {
328
0
                XFREE(rng, NULL, DYNAMIC_TYPE_RNG);
329
0
                rng = NULL;
330
0
            }
331
0
#endif
332
0
        }
333
599
    }
334
599
    if (ret == NULL) {
335
0
#ifdef HAVE_GLOBAL_RNG
336
0
        WOLFSSL_MSG("trying global RNG");
337
0
#endif
338
0
        ret = wolfssl_make_global_rng();
339
0
    }
340
341
599
    return ret;
342
599
}
343
#endif
344
345
#ifdef OPENSSL_EXTRA
346
    /* WOLFSSL_NO_OPENSSL_RAND_CB: Allows way to reduce code size for
347
     *                OPENSSL_EXTRA where RAND callbacks are not used */
348
    #ifndef WOLFSSL_NO_OPENSSL_RAND_CB
349
        static const WOLFSSL_RAND_METHOD* gRandMethods = NULL;
350
        static wolfSSL_Mutex gRandMethodMutex
351
            WOLFSSL_MUTEX_INITIALIZER_CLAUSE(gRandMethodMutex);
352
        #ifndef WOLFSSL_MUTEX_INITIALIZER
353
        static int gRandMethodsInit = 0;
354
        #endif
355
    #endif /* !WOLFSSL_NO_OPENSSL_RAND_CB */
356
#endif /* OPENSSL_EXTRA */
357
358
#define WOLFSSL_SSL_BN_INCLUDED
359
#include "src/ssl_bn.c"
360
361
#ifndef OPENSSL_EXTRA_NO_ASN1
362
#define WOLFSSL_SSL_ASN1_INCLUDED
363
#include "src/ssl_asn1.c"
364
#endif /* OPENSSL_EXTRA_NO_ASN1 */
365
366
#define WOLFSSL_PK_INCLUDED
367
#include "src/pk.c"
368
369
#define WOLFSSL_EVP_PK_INCLUDED
370
#include "wolfcrypt/src/evp_pk.c"
371
372
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
373
/* copies over data of "in" to "out" */
374
static void wolfSSL_CIPHER_copy(WOLFSSL_CIPHER* in, WOLFSSL_CIPHER* out)
375
0
{
376
0
    if (in == NULL || out == NULL)
377
0
        return;
378
379
0
    *out = *in;
380
0
}
381
382
383
#if defined(OPENSSL_ALL)
384
static WOLFSSL_X509_OBJECT* wolfSSL_X509_OBJECT_dup(WOLFSSL_X509_OBJECT* obj)
385
0
{
386
0
    WOLFSSL_X509_OBJECT* ret = NULL;
387
0
    if (obj) {
388
0
        ret = wolfSSL_X509_OBJECT_new();
389
0
        if (ret) {
390
0
            ret->type = obj->type;
391
0
            switch (ret->type) {
392
0
                case WOLFSSL_X509_LU_NONE:
393
0
                    break;
394
0
                case WOLFSSL_X509_LU_X509:
395
0
                    ret->data.x509 = wolfSSL_X509_dup(obj->data.x509);
396
0
                    break;
397
0
                case WOLFSSL_X509_LU_CRL:
398
            #if defined(HAVE_CRL)
399
                    ret->data.crl = wolfSSL_X509_CRL_dup(obj->data.crl);
400
            #endif
401
0
                    break;
402
0
            }
403
0
        }
404
0
    }
405
0
    return ret;
406
0
}
407
#endif /* OPENSSL_ALL */
408
409
#endif /* OPENSSL_EXTRA || WOLFSSL_WPAS_SMALL */
410
411
#define WOLFSSL_SSL_SK_INCLUDED
412
#include "src/ssl_sk.c"
413
414
415
#include <wolfssl/wolfcrypt/hpke.h>
416
417
#define WOLFSSL_SSL_ECH_INCLUDED
418
#include "src/ssl_ech.c"
419
420
#ifdef OPENSSL_EXTRA
421
static int wolfSSL_parse_cipher_list(WOLFSSL_CTX* ctx, WOLFSSL* ssl,
422
        Suites* suites, const char* list);
423
#endif
424
425
#if defined(WOLFSSL_RENESAS_TSIP_TLS) || defined(WOLFSSL_RENESAS_FSPSM_TLS)
426
#include <wolfssl/wolfcrypt/port/Renesas/renesas_cmn.h>
427
#endif
428
429
/* prevent multiple mutex initializations */
430
431
/* note, initRefCount is not used for thread synchronization, only for
432
 * bookkeeping while inits_count_mutex is held.
433
 */
434
static volatile WC_THREADSHARED int initRefCount = 0;
435
436
/* init ref count mutex */
437
static WC_THREADSHARED wolfSSL_Mutex inits_count_mutex
438
    WOLFSSL_MUTEX_INITIALIZER_CLAUSE(inits_count_mutex);
439
#ifndef WOLFSSL_MUTEX_INITIALIZER
440
static WC_THREADSHARED volatile int inits_count_mutex_valid = 0;
441
#endif
442
443
#ifdef NO_TLS
444
static const WOLFSSL_METHOD gNoTlsMethod;
445
#endif
446
447
/* Create a new WOLFSSL_CTX struct and return the pointer to created struct.
448
   WOLFSSL_METHOD pointer passed in is given to ctx to manage.
449
   This function frees the passed in WOLFSSL_METHOD struct on failure and on
450
   success is freed when ctx is freed.
451
 */
452
WOLFSSL_CTX* wolfSSL_CTX_new_ex(WOLFSSL_METHOD* method, void* heap)
453
4.78k
{
454
4.78k
    WOLFSSL_CTX* ctx = NULL;
455
456
4.78k
    WOLFSSL_ENTER("wolfSSL_CTX_new_ex");
457
458
4.78k
    if (initRefCount == 0) {
459
        /* user no longer forced to call Init themselves */
460
0
        int ret = wolfSSL_Init();
461
0
        if (ret != WOLFSSL_SUCCESS) {
462
0
            WOLFSSL_MSG("wolfSSL_Init failed");
463
0
            WOLFSSL_LEAVE("wolfSSL_CTX_new_ex", 0);
464
0
            XFREE(method, heap, DYNAMIC_TYPE_METHOD);
465
0
            return NULL;
466
0
        }
467
0
    }
468
469
4.78k
#ifndef NO_TLS
470
4.78k
    if (method == NULL)
471
0
        return ctx;
472
#else
473
    /* a blank TLS method */
474
    method = (WOLFSSL_METHOD*)&gNoTlsMethod;
475
#endif
476
477
4.78k
    ctx = (WOLFSSL_CTX*)XMALLOC(sizeof(WOLFSSL_CTX), heap, DYNAMIC_TYPE_CTX);
478
4.78k
    if (ctx) {
479
4.78k
        int ret;
480
481
4.78k
        ret = InitSSL_Ctx(ctx, method, heap);
482
    #ifdef WOLFSSL_STATIC_MEMORY
483
        if (heap != NULL) {
484
            ctx->onHeapHint = 1; /* free the memory back to heap when done */
485
        }
486
    #endif
487
4.78k
        if (ret < 0) {
488
0
            WOLFSSL_MSG("Init CTX failed");
489
0
            wolfSSL_CTX_free(ctx);
490
0
            ctx = NULL;
491
0
        }
492
#if defined(OPENSSL_EXTRA) && defined(WOLFCRYPT_HAVE_SRP) \
493
                           && !defined(NO_SHA256) && !defined(WC_NO_RNG)
494
        else {
495
            ctx->srp = (Srp*)XMALLOC(sizeof(Srp), heap, DYNAMIC_TYPE_SRP);
496
            if (ctx->srp == NULL){
497
                WOLFSSL_MSG("Init CTX failed");
498
                wolfSSL_CTX_free(ctx);
499
                return NULL;
500
            }
501
            XMEMSET(ctx->srp, 0, sizeof(Srp));
502
        }
503
#endif
504
4.78k
    }
505
0
    else {
506
0
        WOLFSSL_MSG("Alloc CTX failed, method freed");
507
0
        XFREE(method, heap, DYNAMIC_TYPE_METHOD);
508
0
    }
509
510
#ifdef OPENSSL_COMPATIBLE_DEFAULTS
511
    if (ctx) {
512
        wolfSSL_CTX_set_verify(ctx, WOLFSSL_VERIFY_NONE, NULL);
513
        wolfSSL_CTX_set_mode(ctx, WOLFSSL_MODE_AUTO_RETRY);
514
        if (wolfSSL_CTX_set_min_proto_version(ctx,
515
                (method->version.major == DTLS_MAJOR) ?
516
                DTLS1_VERSION : SSL3_VERSION) != WOLFSSL_SUCCESS ||
517
#ifdef HAVE_ANON
518
                wolfSSL_CTX_allow_anon_cipher(ctx) != WOLFSSL_SUCCESS ||
519
#endif
520
                wolfSSL_CTX_set_group_messages(ctx) != WOLFSSL_SUCCESS) {
521
            WOLFSSL_MSG("Setting OpenSSL CTX defaults failed");
522
            wolfSSL_CTX_free(ctx);
523
            ctx = NULL;
524
        }
525
    }
526
#endif
527
528
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
529
    /* Load the crypto-policy ciphers if configured. */
530
    if (ctx && wolfSSL_crypto_policy_is_enabled()) {
531
        const char * list = wolfSSL_crypto_policy_get_ciphers();
532
        int          ret = 0;
533
534
        if (list != NULL && *list != '\0') {
535
            if (AllocateCtxSuites(ctx) != 0) {
536
                WOLFSSL_MSG("allocate ctx suites failed");
537
                wolfSSL_CTX_free(ctx);
538
                ctx = NULL;
539
            }
540
            else {
541
                ret = wolfSSL_parse_cipher_list(ctx, NULL, ctx->suites, list);
542
                if (ret != WOLFSSL_SUCCESS) {
543
                    WOLFSSL_MSG("parse cipher list failed");
544
                    wolfSSL_CTX_free(ctx);
545
                    ctx = NULL;
546
                }
547
            }
548
        }
549
    }
550
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
551
552
4.78k
    WOLFSSL_LEAVE("wolfSSL_CTX_new_ex", 0);
553
4.78k
    return ctx;
554
4.78k
}
555
556
557
WOLFSSL_ABI
558
WOLFSSL_CTX* wolfSSL_CTX_new(WOLFSSL_METHOD* method)
559
4.83k
{
560
#ifdef WOLFSSL_HEAP_TEST
561
    /* if testing the heap hint then set top level CTX to have test value */
562
    return wolfSSL_CTX_new_ex(method, (void*)WOLFSSL_HEAP_TEST);
563
#else
564
4.83k
    return wolfSSL_CTX_new_ex(method, NULL);
565
4.83k
#endif
566
4.83k
}
567
568
/* increases CTX reference count to track proper time to "free" */
569
int wolfSSL_CTX_up_ref(WOLFSSL_CTX* ctx)
570
81.1k
{
571
81.1k
    int ret;
572
81.1k
    wolfSSL_RefWithMutexInc(&ctx->ref, &ret);
573
#ifdef WOLFSSL_REFCNT_ERROR_RETURN
574
    return ((ret == 0) ? WOLFSSL_SUCCESS : WOLFSSL_FAILURE);
575
#else
576
81.1k
    (void)ret;
577
81.1k
    return WOLFSSL_SUCCESS;
578
81.1k
#endif
579
81.1k
}
580
581
WOLFSSL_ABI
582
void wolfSSL_CTX_free(WOLFSSL_CTX* ctx)
583
4.78k
{
584
4.78k
    WOLFSSL_ENTER("wolfSSL_CTX_free");
585
4.78k
    if (ctx) {
586
4.78k
        FreeSSL_Ctx(ctx);
587
4.78k
    }
588
589
4.78k
    WOLFSSL_LEAVE("wolfSSL_CTX_free", 0);
590
4.78k
}
591
592
593
#ifdef HAVE_ENCRYPT_THEN_MAC
594
/**
595
 * Sets whether Encrypt-Then-MAC extension can be negotiated against context.
596
 * The default value: enabled.
597
 *
598
 * ctx  SSL/TLS context.
599
 * set  Whether to allow or not: 1 is allow and 0 is disallow.
600
 * returns WOLFSSL_SUCCESS
601
 */
602
int wolfSSL_CTX_AllowEncryptThenMac(WOLFSSL_CTX *ctx, int set)
603
0
{
604
0
    ctx->disallowEncThenMac = !set;
605
0
    return WOLFSSL_SUCCESS;
606
0
}
607
608
/**
609
 * Sets whether Encrypt-Then-MAC extension can be negotiated against context.
610
 * The default value comes from context.
611
 *
612
 * ctx  SSL/TLS context.
613
 * set  Whether to allow or not: 1 is allow and 0 is disallow.
614
 * returns WOLFSSL_SUCCESS
615
 */
616
int wolfSSL_AllowEncryptThenMac(WOLFSSL *ssl, int set)
617
0
{
618
0
    ssl->options.disallowEncThenMac = !set;
619
0
    return WOLFSSL_SUCCESS;
620
0
}
621
#endif
622
623
#ifdef SINGLE_THREADED
624
/* no locking in single threaded mode, allow a CTX level rng to be shared with
625
 * WOLFSSL objects, WOLFSSL_SUCCESS on ok */
626
int wolfSSL_CTX_new_rng(WOLFSSL_CTX* ctx)
627
{
628
    WC_RNG* rng;
629
    int     ret;
630
631
    if (ctx == NULL) {
632
        return BAD_FUNC_ARG;
633
    }
634
635
    rng = (WC_RNG*)XMALLOC(sizeof(WC_RNG), ctx->heap, DYNAMIC_TYPE_RNG);
636
    if (rng == NULL) {
637
        return MEMORY_E;
638
    }
639
640
#ifndef HAVE_FIPS
641
    ret = wc_InitRng_ex(rng, ctx->heap, ctx->devId);
642
#else
643
    ret = wc_InitRng(rng);
644
#endif
645
    if (ret != 0) {
646
        XFREE(rng, ctx->heap, DYNAMIC_TYPE_RNG);
647
        return ret;
648
    }
649
650
    ctx->rng = rng;
651
    return WOLFSSL_SUCCESS;
652
}
653
#endif
654
655
656
WOLFSSL_ABI
657
WOLFSSL* wolfSSL_new(WOLFSSL_CTX* ctx)
658
81.3k
{
659
81.3k
    WOLFSSL* ssl = NULL;
660
81.3k
    int ret = 0;
661
662
81.3k
    WOLFSSL_ENTER("wolfSSL_new");
663
664
81.3k
    if (ctx == NULL) {
665
0
        WOLFSSL_MSG("wolfSSL_new ctx is null");
666
0
        return NULL;
667
0
    }
668
669
81.3k
    ssl = (WOLFSSL*) XMALLOC(sizeof(WOLFSSL), ctx->heap, DYNAMIC_TYPE_SSL);
670
671
81.3k
    if (ssl == NULL) {
672
8
        WOLFSSL_MSG_EX("ssl xmalloc failed to allocate %d bytes",
673
8
                        (int)sizeof(WOLFSSL));
674
8
    }
675
81.3k
    else {
676
81.3k
        ret = InitSSL(ssl, ctx, 0);
677
81.3k
        if (ret < 0) {
678
5.23k
            WOLFSSL_MSG_EX("wolfSSL_new failed during InitSSL. err = %d", ret);
679
5.23k
            FreeSSL(ssl, ctx->heap);
680
5.23k
            ssl = NULL;
681
5.23k
        }
682
76.1k
        else if (ret == 0) {
683
76.1k
            WOLFSSL_MSG("wolfSSL_new InitSSL success");
684
76.1k
        }
685
0
        else {
686
            /* Only success (0) or negative values should ever be seen. */
687
0
            WOLFSSL_MSG_EX("WARNING: wolfSSL_new unexpected InitSSL return"
688
0
                           " value = %d", ret);
689
0
        } /* InitSSL check */
690
81.3k
    } /* ssl XMALLOC success */
691
692
81.3k
    WOLFSSL_LEAVE("wolfSSL_new InitSSL =", ret);
693
81.3k
    (void)ret;
694
695
81.3k
    return ssl;
696
81.3k
}
697
698
699
WOLFSSL_ABI
700
void wolfSSL_free(WOLFSSL* ssl)
701
76.2k
{
702
76.2k
    WOLFSSL_ENTER("wolfSSL_free");
703
704
76.2k
    if (ssl) {
705
76.1k
        WOLFSSL_MSG_EX("Free SSL: %p", (wc_ptr_t)ssl);
706
76.1k
        FreeSSL(ssl, ssl->ctx->heap);
707
76.1k
    }
708
125
    else {
709
125
        WOLFSSL_MSG("Free SSL: wolfSSL_free already null");
710
125
    }
711
76.2k
    WOLFSSL_LEAVE("wolfSSL_free", 0);
712
76.2k
}
713
714
715
int wolfSSL_is_server(WOLFSSL* ssl)
716
0
{
717
0
    if (ssl == NULL)
718
0
        return BAD_FUNC_ARG;
719
0
    return ssl->options.side == WOLFSSL_SERVER_END;
720
0
}
721
722
#ifdef HAVE_WRITE_DUP
723
724
/*
725
 * Release resources around WriteDup object
726
 *
727
 * ssl WOLFSSL object
728
 *
729
 * no return, destruction so make best attempt
730
*/
731
void FreeWriteDup(WOLFSSL* ssl)
732
{
733
    int doFree = 0;
734
735
    WOLFSSL_ENTER("FreeWriteDup");
736
737
    if (ssl->dupWrite) {
738
        if (wc_LockMutex(&ssl->dupWrite->dupMutex) == 0) {
739
            ssl->dupWrite->dupCount--;
740
            if (ssl->dupWrite->dupCount == 0) {
741
                doFree = 1;
742
            } else {
743
                WOLFSSL_MSG("WriteDup count not zero, no full free");
744
            }
745
            wc_UnLockMutex(&ssl->dupWrite->dupMutex);
746
        }
747
    }
748
749
    if (doFree) {
750
        WOLFSSL_MSG("Doing WriteDup full free, count to zero");
751
        wc_FreeMutex(&ssl->dupWrite->dupMutex);
752
        XFREE(ssl->dupWrite, ssl->heap, DYNAMIC_TYPE_WRITEDUP);
753
    }
754
}
755
756
757
/*
758
 * duplicate existing ssl members into dup needed for writing
759
 *
760
 * dup write only WOLFSSL
761
 * ssl existing WOLFSSL
762
 *
763
 * 0 on success
764
*/
765
static int DupSSL(WOLFSSL* dup, WOLFSSL* ssl)
766
{
767
    word16 tmp_weOwnRng;
768
769
    /* shared dupWrite setup */
770
    ssl->dupWrite = (WriteDup*)XMALLOC(sizeof(WriteDup), ssl->heap,
771
                                       DYNAMIC_TYPE_WRITEDUP);
772
    if (ssl->dupWrite == NULL) {
773
        return MEMORY_E;
774
    }
775
    XMEMSET(ssl->dupWrite, 0, sizeof(WriteDup));
776
777
    if (wc_InitMutex(&ssl->dupWrite->dupMutex) != 0) {
778
        XFREE(ssl->dupWrite, ssl->heap, DYNAMIC_TYPE_WRITEDUP);
779
        ssl->dupWrite = NULL;
780
        return BAD_MUTEX_E;
781
    }
782
    ssl->dupWrite->dupCount = 2;    /* both sides have a count to start */
783
    dup->dupWrite = ssl->dupWrite; /* each side uses */
784
785
    tmp_weOwnRng = dup->options.weOwnRng;
786
787
    /* copy write parts over to dup writer */
788
    XMEMCPY(&dup->specs,   &ssl->specs,   sizeof(CipherSpecs));
789
    XMEMCPY(&dup->options, &ssl->options, sizeof(Options));
790
    XMEMCPY(&dup->keys,    &ssl->keys,    sizeof(Keys));
791
    XMEMCPY(&dup->encrypt, &ssl->encrypt, sizeof(Ciphers));
792
    XMEMCPY(&dup->version, &ssl->version, sizeof(ProtocolVersion));
793
    XMEMCPY(&dup->chVersion, &ssl->chVersion, sizeof(ProtocolVersion));
794
795
#ifdef HAVE_ONE_TIME_AUTH
796
#ifdef HAVE_POLY1305
797
    if (ssl->auth.setup && ssl->auth.poly1305 != NULL) {
798
        dup->auth.poly1305 = (Poly1305*)XMALLOC(sizeof(Poly1305), dup->heap,
799
            DYNAMIC_TYPE_CIPHER);
800
        if (dup->auth.poly1305 == NULL)
801
            return MEMORY_E;
802
        dup->auth.setup = 1;
803
    }
804
#endif
805
#endif
806
807
    /* dup side now owns encrypt/write ciphers */
808
    XMEMSET(&ssl->encrypt, 0, sizeof(Ciphers));
809
810
    dup->IOCB_WriteCtx = ssl->IOCB_WriteCtx;
811
    dup->CBIOSend = ssl->CBIOSend;
812
#ifdef OPENSSL_EXTRA
813
    dup->cbioFlag = ssl->cbioFlag;
814
#endif
815
    dup->wfd    = ssl->wfd;
816
    dup->wflags = ssl->wflags;
817
#ifndef WOLFSSL_AEAD_ONLY
818
    dup->hmac   = ssl->hmac;
819
#endif
820
#ifdef HAVE_TRUNCATED_HMAC
821
    dup->truncated_hmac = ssl->truncated_hmac;
822
#endif
823
824
    /* Restore rng option */
825
    dup->options.weOwnRng = tmp_weOwnRng;
826
827
    /* unique side dup setup */
828
    dup->dupSide = WRITE_DUP_SIDE;
829
    ssl->dupSide = READ_DUP_SIDE;
830
831
    return 0;
832
}
833
834
835
/*
836
 * duplicate a WOLFSSL object post handshake for writing only
837
 * turn existing object into read only.  Allows concurrent access from two
838
 * different threads.
839
 *
840
 * ssl existing WOLFSSL object
841
 *
842
 * return dup'd WOLFSSL object on success
843
*/
844
WOLFSSL* wolfSSL_write_dup(WOLFSSL* ssl)
845
{
846
    WOLFSSL* dup = NULL;
847
    int ret = 0;
848
849
    (void)ret;
850
    WOLFSSL_ENTER("wolfSSL_write_dup");
851
852
    if (ssl == NULL) {
853
        return ssl;
854
    }
855
856
    if (ssl->options.handShakeDone == 0) {
857
        WOLFSSL_MSG("wolfSSL_write_dup called before handshake complete");
858
        return NULL;
859
    }
860
861
    if (ssl->dupWrite) {
862
        WOLFSSL_MSG("wolfSSL_write_dup already called once");
863
        return NULL;
864
    }
865
866
    dup = (WOLFSSL*) XMALLOC(sizeof(WOLFSSL), ssl->ctx->heap, DYNAMIC_TYPE_SSL);
867
    if (dup) {
868
        if ( (ret = InitSSL(dup, ssl->ctx, 1)) < 0) {
869
            FreeSSL(dup, ssl->ctx->heap);
870
            dup = NULL;
871
        } else if ( (ret = DupSSL(dup, ssl)) < 0) {
872
            FreeSSL(dup, ssl->ctx->heap);
873
            dup = NULL;
874
        }
875
    }
876
877
    WOLFSSL_LEAVE("wolfSSL_write_dup", ret);
878
879
    return dup;
880
}
881
882
883
/*
884
 * Notify write dup side of fatal error or close notify
885
 *
886
 * ssl WOLFSSL object
887
 * err Notify err
888
 *
889
 * 0 on success
890
*/
891
int NotifyWriteSide(WOLFSSL* ssl, int err)
892
{
893
    int ret;
894
895
    WOLFSSL_ENTER("NotifyWriteSide");
896
897
    ret = wc_LockMutex(&ssl->dupWrite->dupMutex);
898
    if (ret == 0) {
899
        ssl->dupWrite->dupErr = err;
900
        ret = wc_UnLockMutex(&ssl->dupWrite->dupMutex);
901
    }
902
903
    return ret;
904
}
905
906
907
#endif /* HAVE_WRITE_DUP */
908
909
910
#ifdef HAVE_POLY1305
911
/* set if to use old poly 1 for yes 0 to use new poly */
912
int wolfSSL_use_old_poly(WOLFSSL* ssl, int value)
913
0
{
914
0
    (void)ssl;
915
0
    (void)value;
916
917
0
#ifndef WOLFSSL_NO_TLS12
918
0
    WOLFSSL_ENTER("wolfSSL_use_old_poly");
919
0
    WOLFSSL_MSG("Warning SSL connection auto detects old/new and this function"
920
0
            "is depreciated");
921
0
    ssl->options.oldPoly = (word16)value;
922
0
    WOLFSSL_LEAVE("wolfSSL_use_old_poly", 0);
923
0
#endif
924
0
    return 0;
925
0
}
926
#endif
927
928
929
WOLFSSL_ABI
930
int wolfSSL_set_fd(WOLFSSL* ssl, int fd)
931
0
{
932
0
    int ret;
933
934
0
    WOLFSSL_ENTER("wolfSSL_set_fd");
935
936
0
    if (ssl == NULL) {
937
0
        return BAD_FUNC_ARG;
938
0
    }
939
940
0
    ret = wolfSSL_set_read_fd(ssl, fd);
941
0
    if (ret == WOLFSSL_SUCCESS) {
942
0
        ret = wolfSSL_set_write_fd(ssl, fd);
943
0
    }
944
945
0
    return ret;
946
0
}
947
948
#ifdef WOLFSSL_DTLS
949
int wolfSSL_set_dtls_fd_connected(WOLFSSL* ssl, int fd)
950
{
951
    int ret;
952
953
    WOLFSSL_ENTER("wolfSSL_set_dtls_fd_connected");
954
955
    if (ssl == NULL) {
956
        return BAD_FUNC_ARG;
957
    }
958
959
    ret = wolfSSL_set_fd(ssl, fd);
960
    if (ret == WOLFSSL_SUCCESS)
961
        ssl->buffers.dtlsCtx.connected = 1;
962
963
    return ret;
964
}
965
#endif
966
967
968
int wolfSSL_set_read_fd(WOLFSSL* ssl, int fd)
969
0
{
970
0
    WOLFSSL_ENTER("wolfSSL_set_read_fd");
971
972
0
    if (ssl == NULL) {
973
0
        return BAD_FUNC_ARG;
974
0
    }
975
976
0
    ssl->rfd = fd;      /* not used directly to allow IO callbacks */
977
0
    ssl->IOCB_ReadCtx  = &ssl->rfd;
978
979
    #ifdef WOLFSSL_DTLS
980
        ssl->buffers.dtlsCtx.connected = 0;
981
        if (ssl->options.dtls) {
982
            ssl->IOCB_ReadCtx = &ssl->buffers.dtlsCtx;
983
            ssl->buffers.dtlsCtx.rfd = fd;
984
        }
985
    #endif
986
987
0
    WOLFSSL_LEAVE("wolfSSL_set_read_fd", WOLFSSL_SUCCESS);
988
0
    return WOLFSSL_SUCCESS;
989
0
}
990
991
992
int wolfSSL_set_write_fd(WOLFSSL* ssl, int fd)
993
0
{
994
0
    WOLFSSL_ENTER("wolfSSL_set_write_fd");
995
996
0
    if (ssl == NULL) {
997
0
        return BAD_FUNC_ARG;
998
0
    }
999
1000
0
    ssl->wfd = fd;      /* not used directly to allow IO callbacks */
1001
0
    ssl->IOCB_WriteCtx  = &ssl->wfd;
1002
1003
    #ifdef WOLFSSL_DTLS
1004
        ssl->buffers.dtlsCtx.connected = 0;
1005
        if (ssl->options.dtls) {
1006
            ssl->IOCB_WriteCtx = &ssl->buffers.dtlsCtx;
1007
            ssl->buffers.dtlsCtx.wfd = fd;
1008
        }
1009
    #endif
1010
1011
0
    WOLFSSL_LEAVE("wolfSSL_set_write_fd", WOLFSSL_SUCCESS);
1012
0
    return WOLFSSL_SUCCESS;
1013
0
}
1014
1015
1016
/**
1017
  * Get the name of cipher at priority level passed in.
1018
  */
1019
char* wolfSSL_get_cipher_list(int priority)
1020
0
{
1021
0
    const CipherSuiteInfo* ciphers = GetCipherNames();
1022
1023
0
    if (priority >= GetCipherNamesSize() || priority < 0) {
1024
0
        return 0;
1025
0
    }
1026
1027
0
    return (char*)ciphers[priority].name;
1028
0
}
1029
1030
1031
/**
1032
  * Get the name of cipher at priority level passed in.
1033
  */
1034
char* wolfSSL_get_cipher_list_ex(WOLFSSL* ssl, int priority)
1035
0
{
1036
1037
0
    if (ssl == NULL) {
1038
0
        return NULL;
1039
0
    }
1040
0
    else {
1041
0
        const char* cipher;
1042
1043
0
        if ((cipher = wolfSSL_get_cipher_name_internal(ssl)) != NULL) {
1044
0
            if (priority == 0) {
1045
0
                return (char*)cipher;
1046
0
            }
1047
0
            else {
1048
0
                return NULL;
1049
0
            }
1050
0
        }
1051
0
        else {
1052
0
            return wolfSSL_get_cipher_list(priority);
1053
0
        }
1054
0
    }
1055
0
}
1056
1057
1058
int wolfSSL_get_ciphers(char* buf, int len)
1059
0
{
1060
0
    const CipherSuiteInfo* ciphers = GetCipherNames();
1061
0
    int ciphersSz = GetCipherNamesSize();
1062
0
    int i;
1063
1064
0
    if (buf == NULL || len <= 0)
1065
0
        return BAD_FUNC_ARG;
1066
1067
    /* Add each member to the buffer delimited by a : */
1068
0
    for (i = 0; i < ciphersSz; i++) {
1069
0
        int cipherNameSz = (int)XSTRLEN(ciphers[i].name);
1070
0
        if (cipherNameSz + 1 < len) {
1071
0
            XSTRNCPY(buf, ciphers[i].name, (size_t)len);
1072
0
            buf += cipherNameSz;
1073
1074
0
            if (i < ciphersSz - 1)
1075
0
                *buf++ = ':';
1076
0
            *buf = 0;
1077
1078
0
            len -= cipherNameSz + 1;
1079
0
        }
1080
0
        else
1081
0
            return BUFFER_E;
1082
0
    }
1083
0
    return WOLFSSL_SUCCESS;
1084
0
}
1085
1086
1087
#ifndef NO_ERROR_STRINGS
1088
/* places a list of all supported cipher suites in TLS_* format into "buf"
1089
 * return WOLFSSL_SUCCESS on success */
1090
int wolfSSL_get_ciphers_iana(char* buf, int len)
1091
0
{
1092
0
    const CipherSuiteInfo* ciphers = GetCipherNames();
1093
0
    int ciphersSz = GetCipherNamesSize();
1094
0
    int i;
1095
0
    int cipherNameSz;
1096
1097
0
    if (buf == NULL || len <= 0)
1098
0
        return BAD_FUNC_ARG;
1099
1100
    /* Add each member to the buffer delimited by a : */
1101
0
    for (i = 0; i < ciphersSz; i++) {
1102
0
#ifndef NO_CIPHER_SUITE_ALIASES
1103
0
        if (ciphers[i].flags & WOLFSSL_CIPHER_SUITE_FLAG_NAMEALIAS)
1104
0
            continue;
1105
0
#endif
1106
0
        cipherNameSz = (int)XSTRLEN(ciphers[i].name_iana);
1107
0
        if (cipherNameSz + 1 < len) {
1108
0
            XSTRNCPY(buf, ciphers[i].name_iana, (size_t)len);
1109
0
            buf += cipherNameSz;
1110
1111
0
            if (i < ciphersSz - 1)
1112
0
                *buf++ = ':';
1113
0
            *buf = 0;
1114
1115
0
            len -= cipherNameSz + 1;
1116
0
        }
1117
0
        else
1118
0
            return BUFFER_E;
1119
0
    }
1120
0
    return WOLFSSL_SUCCESS;
1121
0
}
1122
#endif /* NO_ERROR_STRINGS */
1123
1124
1125
const char* wolfSSL_get_shared_ciphers(WOLFSSL* ssl, char* buf, int len)
1126
0
{
1127
0
    const char* cipher;
1128
1129
0
    if (ssl == NULL)
1130
0
        return NULL;
1131
1132
0
    cipher = wolfSSL_get_cipher_name_iana(ssl);
1133
0
    len = (int)min((word32)len, (word32)(XSTRLEN(cipher) + 1));
1134
0
    XMEMCPY(buf, cipher, (size_t)len);
1135
0
    return buf;
1136
0
}
1137
1138
int wolfSSL_get_fd(const WOLFSSL* ssl)
1139
0
{
1140
0
    int fd = -1;
1141
0
    WOLFSSL_ENTER("wolfSSL_get_fd");
1142
0
    if (ssl) {
1143
0
        fd = ssl->rfd;
1144
0
    }
1145
0
    WOLFSSL_LEAVE("wolfSSL_get_fd", fd);
1146
0
    return fd;
1147
0
}
1148
1149
int wolfSSL_get_wfd(const WOLFSSL* ssl)
1150
0
{
1151
0
    int fd = -1;
1152
0
    WOLFSSL_ENTER("wolfSSL_get_fd");
1153
0
    if (ssl) {
1154
0
        fd = ssl->wfd;
1155
0
    }
1156
0
    WOLFSSL_LEAVE("wolfSSL_get_fd", fd);
1157
0
    return fd;
1158
0
}
1159
1160
1161
int wolfSSL_dtls(WOLFSSL* ssl)
1162
0
{
1163
0
    int dtlsOpt = 0;
1164
0
    if (ssl)
1165
0
        dtlsOpt = ssl->options.dtls;
1166
0
    return dtlsOpt;
1167
0
}
1168
1169
#ifdef WOLFSSL_WOLFSENTRY_HOOKS
1170
1171
int wolfSSL_CTX_set_AcceptFilter(
1172
    WOLFSSL_CTX *ctx,
1173
    NetworkFilterCallback_t AcceptFilter,
1174
    void *AcceptFilter_arg)
1175
{
1176
    if (ctx == NULL)
1177
        return BAD_FUNC_ARG;
1178
    ctx->AcceptFilter = AcceptFilter;
1179
    ctx->AcceptFilter_arg = AcceptFilter_arg;
1180
    return 0;
1181
}
1182
1183
int wolfSSL_set_AcceptFilter(
1184
    WOLFSSL *ssl,
1185
    NetworkFilterCallback_t AcceptFilter,
1186
    void *AcceptFilter_arg)
1187
{
1188
    if (ssl == NULL)
1189
        return BAD_FUNC_ARG;
1190
    ssl->AcceptFilter = AcceptFilter;
1191
    ssl->AcceptFilter_arg = AcceptFilter_arg;
1192
    return 0;
1193
}
1194
1195
int wolfSSL_CTX_set_ConnectFilter(
1196
    WOLFSSL_CTX *ctx,
1197
    NetworkFilterCallback_t ConnectFilter,
1198
    void *ConnectFilter_arg)
1199
{
1200
    if (ctx == NULL)
1201
        return BAD_FUNC_ARG;
1202
    ctx->ConnectFilter = ConnectFilter;
1203
    ctx->ConnectFilter_arg = ConnectFilter_arg;
1204
    return 0;
1205
}
1206
1207
int wolfSSL_set_ConnectFilter(
1208
    WOLFSSL *ssl,
1209
    NetworkFilterCallback_t ConnectFilter,
1210
    void *ConnectFilter_arg)
1211
{
1212
    if (ssl == NULL)
1213
        return BAD_FUNC_ARG;
1214
    ssl->ConnectFilter = ConnectFilter;
1215
    ssl->ConnectFilter_arg = ConnectFilter_arg;
1216
    return 0;
1217
}
1218
1219
#endif /* WOLFSSL_WOLFSENTRY_HOOKS */
1220
1221
#ifndef WOLFSSL_LEANPSK
1222
#if defined(WOLFSSL_DTLS) && defined(XINET_PTON) && \
1223
    !defined(WOLFSSL_NO_SOCK) && defined(HAVE_SOCKADDR)
1224
void* wolfSSL_dtls_create_peer(int port, char* ip)
1225
{
1226
    SOCKADDR_IN *addr;
1227
    addr = (SOCKADDR_IN*)XMALLOC(sizeof(*addr), NULL,
1228
            DYNAMIC_TYPE_SOCKADDR);
1229
    if (addr == NULL) {
1230
        return NULL;
1231
    }
1232
1233
    addr->sin_family = AF_INET;
1234
    addr->sin_port = XHTONS((word16)port);
1235
    if (XINET_PTON(AF_INET, ip, &addr->sin_addr) < 1) {
1236
        XFREE(addr, NULL, DYNAMIC_TYPE_SOCKADDR);
1237
        return NULL;
1238
    }
1239
1240
    return addr;
1241
}
1242
1243
int wolfSSL_dtls_free_peer(void* addr)
1244
{
1245
    XFREE(addr, NULL, DYNAMIC_TYPE_SOCKADDR);
1246
    return WOLFSSL_SUCCESS;
1247
}
1248
#endif
1249
1250
#ifdef WOLFSSL_DTLS
1251
static int SockAddrSet(WOLFSSL_SOCKADDR* sockAddr, void* peer,
1252
                       unsigned int peerSz, void* heap)
1253
{
1254
    if (peer == NULL || peerSz == 0) {
1255
        if (sockAddr->sa != NULL)
1256
            XFREE(sockAddr->sa, heap, DYNAMIC_TYPE_SOCKADDR);
1257
        sockAddr->sa = NULL;
1258
        sockAddr->sz = 0;
1259
        sockAddr->bufSz = 0;
1260
        return WOLFSSL_SUCCESS;
1261
    }
1262
1263
    if (peerSz > sockAddr->bufSz) {
1264
        if (sockAddr->sa != NULL)
1265
            XFREE(sockAddr->sa, heap, DYNAMIC_TYPE_SOCKADDR);
1266
        sockAddr->sa =
1267
                (void*)XMALLOC(peerSz, heap, DYNAMIC_TYPE_SOCKADDR);
1268
        if (sockAddr->sa == NULL) {
1269
            sockAddr->sz = 0;
1270
            sockAddr->bufSz = 0;
1271
            return WOLFSSL_FAILURE;
1272
        }
1273
        sockAddr->bufSz = peerSz;
1274
    }
1275
    XMEMCPY(sockAddr->sa, peer, peerSz);
1276
    sockAddr->sz = peerSz;
1277
    return WOLFSSL_SUCCESS;
1278
}
1279
#endif
1280
1281
int wolfSSL_dtls_set_peer(WOLFSSL* ssl, void* peer, unsigned int peerSz)
1282
0
{
1283
#ifdef WOLFSSL_DTLS
1284
    int ret;
1285
1286
    if (ssl == NULL)
1287
        return WOLFSSL_FAILURE;
1288
#ifdef WOLFSSL_RW_THREADED
1289
    if (wc_LockRwLock_Wr(&ssl->buffers.dtlsCtx.peerLock) != 0)
1290
        return WOLFSSL_FAILURE;
1291
#endif
1292
    ret = SockAddrSet(&ssl->buffers.dtlsCtx.peer, peer, peerSz, ssl->heap);
1293
    if (ret == WOLFSSL_SUCCESS && !(peer == NULL || peerSz == 0))
1294
        ssl->buffers.dtlsCtx.userSet = 1;
1295
    else
1296
        ssl->buffers.dtlsCtx.userSet = 0;
1297
#ifdef WOLFSSL_RW_THREADED
1298
    if (wc_UnLockRwLock(&ssl->buffers.dtlsCtx.peerLock) != 0)
1299
        ret = WOLFSSL_FAILURE;
1300
#endif
1301
    return ret;
1302
#else
1303
0
    (void)ssl;
1304
0
    (void)peer;
1305
0
    (void)peerSz;
1306
0
    return WOLFSSL_NOT_IMPLEMENTED;
1307
0
#endif
1308
0
}
1309
1310
#if defined(WOLFSSL_DTLS_CID) && !defined(WOLFSSL_NO_SOCK)
1311
int wolfSSL_dtls_set_pending_peer(WOLFSSL* ssl, void* peer, unsigned int peerSz)
1312
{
1313
#ifdef WOLFSSL_DTLS
1314
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
1315
1316
    if (ssl == NULL)
1317
        return WOLFSSL_FAILURE;
1318
#ifdef WOLFSSL_RW_THREADED
1319
    if (wc_LockRwLock_Rd(&ssl->buffers.dtlsCtx.peerLock) != 0)
1320
        return WOLFSSL_FAILURE;
1321
#endif
1322
    if (ssl->buffers.dtlsCtx.peer.sa != NULL &&
1323
            ssl->buffers.dtlsCtx.peer.sz == peerSz &&
1324
            sockAddrEqual((SOCKADDR_S*)ssl->buffers.dtlsCtx.peer.sa,
1325
                    (XSOCKLENT)ssl->buffers.dtlsCtx.peer.sz, (SOCKADDR_S*)peer,
1326
                    (XSOCKLENT)peerSz)) {
1327
        /* Already the current peer. */
1328
        if (ssl->buffers.dtlsCtx.pendingPeer.sa != NULL) {
1329
            /* Clear any other pendingPeer */
1330
            XFREE(ssl->buffers.dtlsCtx.pendingPeer.sa, ssl->heap,
1331
                  DYNAMIC_TYPE_SOCKADDR);
1332
            ssl->buffers.dtlsCtx.pendingPeer.sa = NULL;
1333
            ssl->buffers.dtlsCtx.pendingPeer.sz = 0;
1334
            ssl->buffers.dtlsCtx.pendingPeer.bufSz = 0;
1335
        }
1336
        ret = WOLFSSL_SUCCESS;
1337
    }
1338
    else {
1339
        ret = SockAddrSet(&ssl->buffers.dtlsCtx.pendingPeer, peer, peerSz,
1340
                ssl->heap);
1341
    }
1342
    if (ret == WOLFSSL_SUCCESS)
1343
        ssl->buffers.dtlsCtx.processingPendingRecord = 0;
1344
#ifdef WOLFSSL_RW_THREADED
1345
    if (wc_UnLockRwLock(&ssl->buffers.dtlsCtx.peerLock) != 0)
1346
        ret = WOLFSSL_FAILURE;
1347
#endif
1348
    return ret;
1349
#else
1350
    (void)ssl;
1351
    (void)peer;
1352
    (void)peerSz;
1353
    return WOLFSSL_NOT_IMPLEMENTED;
1354
#endif
1355
}
1356
#endif /* WOLFSSL_DTLS_CID && !WOLFSSL_NO_SOCK */
1357
1358
int wolfSSL_dtls_get_peer(WOLFSSL* ssl, void* peer, unsigned int* peerSz)
1359
0
{
1360
#ifdef WOLFSSL_DTLS
1361
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
1362
    if (ssl == NULL)
1363
        return WOLFSSL_FAILURE;
1364
#ifdef WOLFSSL_RW_THREADED
1365
    if (wc_LockRwLock_Rd(&ssl->buffers.dtlsCtx.peerLock) != 0)
1366
        return WOLFSSL_FAILURE;
1367
#endif
1368
    if (peer != NULL && peerSz != NULL
1369
            && *peerSz >= ssl->buffers.dtlsCtx.peer.sz
1370
            && ssl->buffers.dtlsCtx.peer.sa != NULL) {
1371
        *peerSz = ssl->buffers.dtlsCtx.peer.sz;
1372
        XMEMCPY(peer, ssl->buffers.dtlsCtx.peer.sa, *peerSz);
1373
        ret = WOLFSSL_SUCCESS;
1374
    }
1375
#ifdef WOLFSSL_RW_THREADED
1376
    if (wc_UnLockRwLock(&ssl->buffers.dtlsCtx.peerLock) != 0)
1377
        ret = WOLFSSL_FAILURE;
1378
#endif
1379
    return ret;
1380
#else
1381
0
    (void)ssl;
1382
0
    (void)peer;
1383
0
    (void)peerSz;
1384
0
    return WOLFSSL_NOT_IMPLEMENTED;
1385
0
#endif
1386
0
}
1387
1388
int wolfSSL_dtls_get0_peer(WOLFSSL* ssl, const void** peer,
1389
                           unsigned int* peerSz)
1390
0
{
1391
#if defined(WOLFSSL_DTLS) && !defined(WOLFSSL_RW_THREADED)
1392
    if (ssl == NULL)
1393
        return WOLFSSL_FAILURE;
1394
1395
    if (peer == NULL || peerSz == NULL)
1396
        return WOLFSSL_FAILURE;
1397
1398
    *peer = ssl->buffers.dtlsCtx.peer.sa;
1399
    *peerSz = ssl->buffers.dtlsCtx.peer.sz;
1400
    return WOLFSSL_SUCCESS;
1401
#else
1402
0
    (void)ssl;
1403
0
    (void)peer;
1404
0
    (void)peerSz;
1405
0
    return WOLFSSL_NOT_IMPLEMENTED;
1406
0
#endif
1407
0
}
1408
1409
1410
#if defined(WOLFSSL_SCTP) && defined(WOLFSSL_DTLS)
1411
1412
int wolfSSL_CTX_dtls_set_sctp(WOLFSSL_CTX* ctx)
1413
{
1414
    WOLFSSL_ENTER("wolfSSL_CTX_dtls_set_sctp");
1415
1416
    if (ctx == NULL)
1417
        return BAD_FUNC_ARG;
1418
1419
    ctx->dtlsSctp = 1;
1420
    return WOLFSSL_SUCCESS;
1421
}
1422
1423
1424
int wolfSSL_dtls_set_sctp(WOLFSSL* ssl)
1425
{
1426
    WOLFSSL_ENTER("wolfSSL_dtls_set_sctp");
1427
1428
    if (ssl == NULL)
1429
        return BAD_FUNC_ARG;
1430
1431
    ssl->options.dtlsSctp = 1;
1432
    return WOLFSSL_SUCCESS;
1433
}
1434
1435
#endif /* WOLFSSL_DTLS && WOLFSSL_SCTP */
1436
1437
#if (defined(WOLFSSL_SCTP) || defined(WOLFSSL_DTLS_MTU)) && \
1438
                                                           defined(WOLFSSL_DTLS)
1439
1440
int wolfSSL_CTX_dtls_set_mtu(WOLFSSL_CTX* ctx, word16 newMtu)
1441
{
1442
    if (ctx == NULL || newMtu > MAX_RECORD_SIZE)
1443
        return BAD_FUNC_ARG;
1444
1445
    ctx->dtlsMtuSz = newMtu;
1446
    return WOLFSSL_SUCCESS;
1447
}
1448
1449
1450
int wolfSSL_dtls_set_mtu(WOLFSSL* ssl, word16 newMtu)
1451
{
1452
    if (ssl == NULL)
1453
        return BAD_FUNC_ARG;
1454
1455
    if (newMtu > MAX_RECORD_SIZE) {
1456
        ssl->error = BAD_FUNC_ARG;
1457
        return WOLFSSL_FAILURE;
1458
    }
1459
1460
    ssl->dtlsMtuSz = newMtu;
1461
    return WOLFSSL_SUCCESS;
1462
}
1463
1464
#ifdef OPENSSL_EXTRA
1465
/* Maps to compatibility API SSL_set_mtu and is same as wolfSSL_dtls_set_mtu,
1466
 * but expects only success or failure returns. */
1467
int wolfSSL_set_mtu_compat(WOLFSSL* ssl, unsigned short mtu)
1468
{
1469
    if (wolfSSL_dtls_set_mtu(ssl, mtu) == WOLFSSL_SUCCESS)
1470
        return WOLFSSL_SUCCESS;
1471
    else
1472
        return WOLFSSL_FAILURE;
1473
}
1474
#endif /* OPENSSL_EXTRA */
1475
1476
#endif /* WOLFSSL_DTLS && (WOLFSSL_SCTP || WOLFSSL_DTLS_MTU) */
1477
1478
#ifdef WOLFSSL_SRTP
1479
1480
static const WOLFSSL_SRTP_PROTECTION_PROFILE gSrtpProfiles[] = {
1481
    /* AES CCM 128, Salt:112-bits, Auth HMAC-SHA1 Tag: 80-bits
1482
     * (master_key:128bits + master_salt:112bits) * 2 = 480 bits (60) */
1483
    {"SRTP_AES128_CM_SHA1_80", SRTP_AES128_CM_SHA1_80,
1484
     (((128 + 112) * 2) / 8) },
1485
    /* AES CCM 128, Salt:112-bits, Auth HMAC-SHA1 Tag: 32-bits
1486
     * (master_key:128bits + master_salt:112bits) * 2 = 480 bits (60) */
1487
    {"SRTP_AES128_CM_SHA1_32", SRTP_AES128_CM_SHA1_32,
1488
     (((128 + 112) * 2) / 8) },
1489
    /* NULL Cipher, Salt:112-bits, Auth HMAC-SHA1 Tag 80-bits */
1490
    {"SRTP_NULL_SHA1_80", SRTP_NULL_SHA1_80, ((112 * 2) / 8)},
1491
    /* NULL Cipher, Salt:112-bits, Auth HMAC-SHA1 Tag 32-bits */
1492
    {"SRTP_NULL_SHA1_32", SRTP_NULL_SHA1_32, ((112 * 2) / 8)},
1493
    /* AES GCM 128, Salt: 96-bits, Auth GCM Tag 128-bits
1494
     * (master_key:128bits + master_salt:96bits) * 2 = 448 bits (56) */
1495
    {"SRTP_AEAD_AES_128_GCM", SRTP_AEAD_AES_128_GCM, (((128 + 96) * 2) / 8) },
1496
    /* AES GCM 256, Salt: 96-bits, Auth GCM Tag 128-bits
1497
     * (master_key:256bits + master_salt:96bits) * 2 = 704 bits (88) */
1498
    {"SRTP_AEAD_AES_256_GCM", SRTP_AEAD_AES_256_GCM, (((256 + 96) * 2) / 8) },
1499
};
1500
1501
static const WOLFSSL_SRTP_PROTECTION_PROFILE* DtlsSrtpFindProfile(
1502
    const char* profile_str, word32 profile_str_len, unsigned long id)
1503
{
1504
    int i;
1505
    const WOLFSSL_SRTP_PROTECTION_PROFILE* profile = NULL;
1506
    for (i=0;
1507
         i<(int)(sizeof(gSrtpProfiles)/sizeof(WOLFSSL_SRTP_PROTECTION_PROFILE));
1508
         i++) {
1509
        if (profile_str != NULL) {
1510
            word32 srtp_profile_len = (word32)XSTRLEN(gSrtpProfiles[i].name);
1511
            if (srtp_profile_len == profile_str_len &&
1512
                XMEMCMP(gSrtpProfiles[i].name, profile_str, profile_str_len)
1513
                                                                         == 0) {
1514
                profile = &gSrtpProfiles[i];
1515
                break;
1516
            }
1517
        }
1518
        else if (id != 0 && gSrtpProfiles[i].id == id) {
1519
            profile = &gSrtpProfiles[i];
1520
            break;
1521
        }
1522
    }
1523
    return profile;
1524
}
1525
1526
/* profile_str: accepts ":" colon separated list of SRTP profiles */
1527
static int DtlsSrtpSelProfiles(word16* id, const char* profile_str)
1528
{
1529
    const WOLFSSL_SRTP_PROTECTION_PROFILE* profile;
1530
    const char *current, *next = NULL;
1531
    word32 length = 0, current_length;
1532
1533
    *id = 0; /* reset destination ID's */
1534
1535
    if (profile_str == NULL) {
1536
        return WOLFSSL_FAILURE;
1537
    }
1538
1539
    /* loop on end of line or colon ":" */
1540
    next = profile_str;
1541
    length = (word32)XSTRLEN(profile_str);
1542
    do {
1543
        current = next;
1544
        next = XSTRSTR(current, ":");
1545
        if (next) {
1546
            current_length = (word32)(next - current);
1547
            ++next; /* ++ needed to skip ':' */
1548
        } else {
1549
            current_length = (word32)XSTRLEN(current);
1550
        }
1551
        if (current_length < length)
1552
            length = current_length;
1553
        profile = DtlsSrtpFindProfile(current, current_length, 0);
1554
        if (profile != NULL) {
1555
            *id |= (1 << profile->id); /* selected bit based on ID */
1556
        }
1557
    } while (next != NULL);
1558
    return WOLFSSL_SUCCESS;
1559
}
1560
1561
/**
1562
 * @brief Set the SRTP protection profiles for DTLS.
1563
 *
1564
 * @param ctx Pointer to the WOLFSSL_CTX structure representing the SSL/TLS
1565
 *            context.
1566
 * @param profile_str A colon-separated string of SRTP profile names.
1567
 * @return 0 on success to match OpenSSL
1568
 * @return 1 on error to match OpenSSL
1569
 */
1570
int wolfSSL_CTX_set_tlsext_use_srtp(WOLFSSL_CTX* ctx, const char* profile_str)
1571
{
1572
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
1573
    if (ctx != NULL) {
1574
        ret = DtlsSrtpSelProfiles(&ctx->dtlsSrtpProfiles, profile_str);
1575
    }
1576
1577
    if (ret == WC_NO_ERR_TRACE(WOLFSSL_FAILURE)) {
1578
        ret = 1;
1579
    } else {
1580
        ret = 0;
1581
    }
1582
1583
    return ret;
1584
}
1585
1586
/**
1587
 * @brief Set the SRTP protection profiles for DTLS.
1588
 *
1589
 * @param ssl Pointer to the WOLFSSL structure representing the SSL/TLS
1590
 *            session.
1591
 * @param profile_str A colon-separated string of SRTP profile names.
1592
 * @return 0 on success to match OpenSSL
1593
 * @return 1 on error to match OpenSSL
1594
 */
1595
int wolfSSL_set_tlsext_use_srtp(WOLFSSL* ssl, const char* profile_str)
1596
{
1597
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
1598
    if (ssl != NULL) {
1599
        ret = DtlsSrtpSelProfiles(&ssl->dtlsSrtpProfiles, profile_str);
1600
    }
1601
1602
    if (ret == WC_NO_ERR_TRACE(WOLFSSL_FAILURE)) {
1603
        ret = 1;
1604
    } else {
1605
        ret = 0;
1606
    }
1607
1608
    return ret;
1609
}
1610
1611
const WOLFSSL_SRTP_PROTECTION_PROFILE* wolfSSL_get_selected_srtp_profile(
1612
    WOLFSSL* ssl)
1613
{
1614
    const WOLFSSL_SRTP_PROTECTION_PROFILE* profile = NULL;
1615
    if (ssl) {
1616
        profile = DtlsSrtpFindProfile(NULL, 0, ssl->dtlsSrtpId);
1617
    }
1618
    return profile;
1619
}
1620
#ifndef NO_WOLFSSL_STUB
1621
WOLF_STACK_OF(WOLFSSL_SRTP_PROTECTION_PROFILE)* wolfSSL_get_srtp_profiles(
1622
    WOLFSSL* ssl)
1623
{
1624
    /* Not yet implemented - should return list of available SRTP profiles
1625
     * ssl->dtlsSrtpProfiles */
1626
    (void)ssl;
1627
    return NULL;
1628
}
1629
#endif
1630
1631
#define DTLS_SRTP_KEYING_MATERIAL_LABEL "EXTRACTOR-dtls_srtp"
1632
1633
int wolfSSL_export_dtls_srtp_keying_material(WOLFSSL* ssl,
1634
    unsigned char* out, size_t* olen)
1635
{
1636
    const WOLFSSL_SRTP_PROTECTION_PROFILE* profile = NULL;
1637
1638
    if (ssl == NULL || olen == NULL) {
1639
        return BAD_FUNC_ARG;
1640
    }
1641
1642
    profile = DtlsSrtpFindProfile(NULL, 0, ssl->dtlsSrtpId);
1643
    if (profile == NULL) {
1644
        WOLFSSL_MSG("Not using DTLS SRTP");
1645
        return EXT_MISSING;
1646
    }
1647
    if (out == NULL) {
1648
        *olen = (size_t)profile->kdfBits;
1649
        return WC_NO_ERR_TRACE(LENGTH_ONLY_E);
1650
    }
1651
1652
    if (*olen < (size_t)profile->kdfBits) {
1653
        return BUFFER_E;
1654
    }
1655
1656
    return wolfSSL_export_keying_material(ssl, out, (size_t)profile->kdfBits,
1657
            DTLS_SRTP_KEYING_MATERIAL_LABEL,
1658
            XSTR_SIZEOF(DTLS_SRTP_KEYING_MATERIAL_LABEL), NULL, 0, 0);
1659
}
1660
1661
#endif /* WOLFSSL_SRTP */
1662
1663
1664
#ifdef WOLFSSL_DTLS_DROP_STATS
1665
1666
int wolfSSL_dtls_get_drop_stats(WOLFSSL* ssl,
1667
                                word32* macDropCount, word32* replayDropCount)
1668
{
1669
    int ret;
1670
1671
    WOLFSSL_ENTER("wolfSSL_dtls_get_drop_stats");
1672
1673
    if (ssl == NULL)
1674
        ret = BAD_FUNC_ARG;
1675
    else {
1676
        ret = WOLFSSL_SUCCESS;
1677
        if (macDropCount != NULL)
1678
            *macDropCount = ssl->macDropCount;
1679
        if (replayDropCount != NULL)
1680
            *replayDropCount = ssl->replayDropCount;
1681
    }
1682
1683
    WOLFSSL_LEAVE("wolfSSL_dtls_get_drop_stats", ret);
1684
    return ret;
1685
}
1686
1687
#endif /* WOLFSSL_DTLS_DROP_STATS */
1688
1689
1690
#if defined(WOLFSSL_MULTICAST)
1691
1692
int wolfSSL_CTX_mcast_set_member_id(WOLFSSL_CTX* ctx, word16 id)
1693
{
1694
    int ret = 0;
1695
1696
    WOLFSSL_ENTER("wolfSSL_CTX_mcast_set_member_id");
1697
1698
    if (ctx == NULL || id > WOLFSSL_MAX_8BIT)
1699
        ret = BAD_FUNC_ARG;
1700
1701
    if (ret == 0) {
1702
        ctx->haveEMS = 0;
1703
        ctx->haveMcast = 1;
1704
        ctx->mcastID = (byte)id;
1705
#ifndef WOLFSSL_USER_IO
1706
        ctx->CBIORecv = EmbedReceiveFromMcast;
1707
#endif /* WOLFSSL_USER_IO */
1708
1709
        ret = WOLFSSL_SUCCESS;
1710
    }
1711
    WOLFSSL_LEAVE("wolfSSL_CTX_mcast_set_member_id", ret);
1712
    return ret;
1713
}
1714
1715
int wolfSSL_mcast_get_max_peers(void)
1716
{
1717
    return WOLFSSL_MULTICAST_PEERS;
1718
}
1719
1720
#ifdef WOLFSSL_DTLS
1721
static WC_INLINE word32 UpdateHighwaterMark(word32 cur, word32 first,
1722
                                         word32 second, word32 high)
1723
{
1724
    word32 newCur = 0;
1725
1726
    if (cur < first)
1727
        newCur = first;
1728
    else if (cur < second)
1729
        newCur = second;
1730
    else if (cur < high)
1731
        newCur = high;
1732
1733
    return newCur;
1734
}
1735
#endif /* WOLFSSL_DTLS */
1736
1737
1738
int wolfSSL_set_secret(WOLFSSL* ssl, word16 epoch,
1739
                       const byte* preMasterSecret, word32 preMasterSz,
1740
                       const byte* clientRandom, const byte* serverRandom,
1741
                       const byte* suite)
1742
{
1743
    int ret = 0;
1744
1745
    WOLFSSL_ENTER("wolfSSL_set_secret");
1746
1747
    if (ssl == NULL || preMasterSecret == NULL ||
1748
        preMasterSz == 0 || preMasterSz > ENCRYPT_LEN ||
1749
        clientRandom == NULL || serverRandom == NULL || suite == NULL) {
1750
1751
        ret = BAD_FUNC_ARG;
1752
    }
1753
1754
    if (ret == 0 && ssl->arrays->preMasterSecret == NULL) {
1755
        ssl->arrays->preMasterSz = ENCRYPT_LEN;
1756
        ssl->arrays->preMasterSecret = (byte*)XMALLOC(ENCRYPT_LEN, ssl->heap,
1757
            DYNAMIC_TYPE_SECRET);
1758
        if (ssl->arrays->preMasterSecret == NULL) {
1759
            ret = MEMORY_E;
1760
        }
1761
    }
1762
1763
    if (ret == 0) {
1764
        XMEMCPY(ssl->arrays->preMasterSecret, preMasterSecret, preMasterSz);
1765
        XMEMSET(ssl->arrays->preMasterSecret + preMasterSz, 0,
1766
            ENCRYPT_LEN - preMasterSz);
1767
        ssl->arrays->preMasterSz = preMasterSz;
1768
        XMEMCPY(ssl->arrays->clientRandom, clientRandom, RAN_LEN);
1769
        XMEMCPY(ssl->arrays->serverRandom, serverRandom, RAN_LEN);
1770
        ssl->options.cipherSuite0 = suite[0];
1771
        ssl->options.cipherSuite = suite[1];
1772
1773
        ret = SetCipherSpecs(ssl);
1774
    }
1775
1776
    if (ret == 0)
1777
        ret = MakeTlsMasterSecret(ssl);
1778
1779
    if (ret == 0) {
1780
        ssl->keys.encryptionOn = 1;
1781
        ret = SetKeysSide(ssl, ENCRYPT_AND_DECRYPT_SIDE);
1782
    }
1783
1784
    if (ret == 0) {
1785
        if (ssl->options.dtls) {
1786
        #ifdef WOLFSSL_DTLS
1787
            WOLFSSL_DTLS_PEERSEQ* peerSeq;
1788
            int i;
1789
1790
            ssl->keys.dtls_epoch = epoch;
1791
            for (i = 0, peerSeq = ssl->keys.peerSeq;
1792
                 i < WOLFSSL_DTLS_PEERSEQ_SZ;
1793
                 i++, peerSeq++) {
1794
1795
                peerSeq->nextEpoch = epoch;
1796
                peerSeq->prevSeq_lo = peerSeq->nextSeq_lo;
1797
                peerSeq->prevSeq_hi = peerSeq->nextSeq_hi;
1798
                peerSeq->nextSeq_lo = 0;
1799
                peerSeq->nextSeq_hi = 0;
1800
                XMEMCPY(peerSeq->prevWindow, peerSeq->window, DTLS_SEQ_SZ);
1801
                XMEMSET(peerSeq->window, 0, DTLS_SEQ_SZ);
1802
                peerSeq->highwaterMark = UpdateHighwaterMark(0,
1803
                        ssl->ctx->mcastFirstSeq,
1804
                        ssl->ctx->mcastSecondSeq,
1805
                        ssl->ctx->mcastMaxSeq);
1806
            }
1807
        #else
1808
            (void)epoch;
1809
        #endif
1810
        }
1811
        FreeHandshakeResources(ssl);
1812
        ret = WOLFSSL_SUCCESS;
1813
    }
1814
    else {
1815
        if (ssl)
1816
            ssl->error = ret;
1817
        ret = WOLFSSL_FATAL_ERROR;
1818
    }
1819
    WOLFSSL_LEAVE("wolfSSL_set_secret", ret);
1820
    return ret;
1821
}
1822
1823
1824
#ifdef WOLFSSL_DTLS
1825
1826
int wolfSSL_mcast_peer_add(WOLFSSL* ssl, word16 peerId, int sub)
1827
{
1828
    WOLFSSL_DTLS_PEERSEQ* p = NULL;
1829
    int ret = WOLFSSL_SUCCESS;
1830
    int i;
1831
1832
    WOLFSSL_ENTER("wolfSSL_mcast_peer_add");
1833
    if (ssl == NULL || peerId > WOLFSSL_MAX_8BIT)
1834
        return BAD_FUNC_ARG;
1835
1836
    if (!sub) {
1837
        /* Make sure it isn't already present, while keeping the first
1838
         * open spot. */
1839
        for (i = 0; i < WOLFSSL_DTLS_PEERSEQ_SZ; i++) {
1840
            if (ssl->keys.peerSeq[i].peerId == INVALID_PEER_ID)
1841
                p = &ssl->keys.peerSeq[i];
1842
            if (ssl->keys.peerSeq[i].peerId == peerId) {
1843
                WOLFSSL_MSG("Peer ID already in multicast peer list.");
1844
                p = NULL;
1845
            }
1846
        }
1847
1848
        if (p != NULL) {
1849
            XMEMSET(p, 0, sizeof(WOLFSSL_DTLS_PEERSEQ));
1850
            p->peerId = peerId;
1851
            p->highwaterMark = UpdateHighwaterMark(0,
1852
                ssl->ctx->mcastFirstSeq,
1853
                ssl->ctx->mcastSecondSeq,
1854
                ssl->ctx->mcastMaxSeq);
1855
        }
1856
        else {
1857
            WOLFSSL_MSG("No room in peer list.");
1858
            ret = WOLFSSL_FATAL_ERROR;
1859
        }
1860
    }
1861
    else {
1862
        for (i = 0; i < WOLFSSL_DTLS_PEERSEQ_SZ; i++) {
1863
            if (ssl->keys.peerSeq[i].peerId == peerId)
1864
                p = &ssl->keys.peerSeq[i];
1865
        }
1866
1867
        if (p != NULL) {
1868
            p->peerId = INVALID_PEER_ID;
1869
        }
1870
        else {
1871
            WOLFSSL_MSG("Peer not found in list.");
1872
        }
1873
    }
1874
1875
    WOLFSSL_LEAVE("wolfSSL_mcast_peer_add", ret);
1876
    return ret;
1877
}
1878
1879
1880
/* If peerId is in the list of peers and its last sequence number is non-zero,
1881
 * return 1, otherwise return 0. */
1882
int wolfSSL_mcast_peer_known(WOLFSSL* ssl, unsigned short peerId)
1883
{
1884
    int known = 0;
1885
    int i;
1886
1887
    WOLFSSL_ENTER("wolfSSL_mcast_peer_known");
1888
1889
    if (ssl == NULL || peerId > WOLFSSL_MAX_8BIT) {
1890
        return BAD_FUNC_ARG;
1891
    }
1892
1893
    for (i = 0; i < WOLFSSL_DTLS_PEERSEQ_SZ; i++) {
1894
        if (ssl->keys.peerSeq[i].peerId == peerId) {
1895
            if (ssl->keys.peerSeq[i].nextSeq_hi ||
1896
                ssl->keys.peerSeq[i].nextSeq_lo) {
1897
1898
                known = 1;
1899
            }
1900
            break;
1901
        }
1902
    }
1903
1904
    WOLFSSL_LEAVE("wolfSSL_mcast_peer_known", known);
1905
    return known;
1906
}
1907
1908
1909
int wolfSSL_CTX_mcast_set_highwater_cb(WOLFSSL_CTX* ctx, word32 maxSeq,
1910
                                       word32 first, word32 second,
1911
                                       CallbackMcastHighwater cb)
1912
{
1913
    if (ctx == NULL || (second && first > second) ||
1914
        first > maxSeq || second > maxSeq || cb == NULL) {
1915
1916
        return BAD_FUNC_ARG;
1917
    }
1918
1919
    ctx->mcastHwCb = cb;
1920
    ctx->mcastFirstSeq = first;
1921
    ctx->mcastSecondSeq = second;
1922
    ctx->mcastMaxSeq = maxSeq;
1923
1924
    return WOLFSSL_SUCCESS;
1925
}
1926
1927
1928
int wolfSSL_mcast_set_highwater_ctx(WOLFSSL* ssl, void* ctx)
1929
{
1930
    if (ssl == NULL || ctx == NULL)
1931
        return BAD_FUNC_ARG;
1932
1933
    ssl->mcastHwCbCtx = ctx;
1934
1935
    return WOLFSSL_SUCCESS;
1936
}
1937
1938
#endif /* WOLFSSL_DTLS */
1939
1940
#endif /* WOLFSSL_MULTICAST */
1941
1942
1943
#endif /* WOLFSSL_LEANPSK */
1944
1945
#ifndef NO_TLS
1946
/* return underlying connect or accept, WOLFSSL_SUCCESS on ok */
1947
int wolfSSL_negotiate(WOLFSSL* ssl)
1948
249
{
1949
249
    int err = WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR);
1950
1951
249
    WOLFSSL_ENTER("wolfSSL_negotiate");
1952
1953
249
    if (ssl == NULL)
1954
0
        return WOLFSSL_FATAL_ERROR;
1955
1956
249
#ifndef NO_WOLFSSL_SERVER
1957
249
    if (ssl->options.side == WOLFSSL_SERVER_END) {
1958
249
#ifdef WOLFSSL_TLS13
1959
249
        if (IsAtLeastTLSv1_3(ssl->version))
1960
249
            err = wolfSSL_accept_TLSv13(ssl);
1961
0
        else
1962
0
#endif
1963
0
            err = wolfSSL_accept(ssl);
1964
249
    }
1965
249
#endif
1966
1967
249
#ifndef NO_WOLFSSL_CLIENT
1968
249
    if (ssl->options.side == WOLFSSL_CLIENT_END) {
1969
0
#ifdef WOLFSSL_TLS13
1970
0
        if (IsAtLeastTLSv1_3(ssl->version))
1971
0
            err = wolfSSL_connect_TLSv13(ssl);
1972
0
        else
1973
0
#endif
1974
0
            err = wolfSSL_connect(ssl);
1975
0
    }
1976
249
#endif
1977
1978
249
    (void)ssl;
1979
1980
249
    WOLFSSL_LEAVE("wolfSSL_negotiate", err);
1981
1982
249
    return err;
1983
249
}
1984
#endif /* !NO_TLS */
1985
1986
WOLFSSL_ABI
1987
WC_RNG* wolfSSL_GetRNG(WOLFSSL* ssl)
1988
0
{
1989
0
    if (ssl) {
1990
0
        return ssl->rng;
1991
0
    }
1992
1993
0
    return NULL;
1994
0
}
1995
1996
1997
#ifndef WOLFSSL_LEANPSK
1998
/* object size based on build */
1999
int wolfSSL_GetObjectSize(void)
2000
0
{
2001
#ifdef SHOW_SIZES
2002
    printf("sizeof suites           = %lu\n", (unsigned long)sizeof(Suites));
2003
    printf("sizeof ciphers(2)       = %lu\n", (unsigned long)sizeof(Ciphers));
2004
#ifndef NO_RC4
2005
    printf("\tsizeof arc4         = %lu\n", (unsigned long)sizeof(Arc4));
2006
#endif
2007
    printf("\tsizeof aes          = %lu\n", (unsigned long)sizeof(Aes));
2008
#ifndef NO_DES3
2009
    printf("\tsizeof des3         = %lu\n", (unsigned long)sizeof(Des3));
2010
#endif
2011
#ifdef HAVE_CHACHA
2012
    printf("\tsizeof chacha       = %lu\n", (unsigned long)sizeof(ChaCha));
2013
#endif
2014
#ifdef WOLFSSL_SM4
2015
    printf("\tsizeof sm4          = %lu\n", (unsigned long)sizeof(Sm4));
2016
#endif
2017
    printf("sizeof cipher specs     = %lu\n", (unsigned long)
2018
        sizeof(CipherSpecs));
2019
    printf("sizeof keys             = %lu\n", (unsigned long)sizeof(Keys));
2020
    printf("sizeof Hashes(2)        = %lu\n", (unsigned long)sizeof(Hashes));
2021
#ifndef NO_MD5
2022
    printf("\tsizeof MD5          = %lu\n", (unsigned long)sizeof(wc_Md5));
2023
#endif
2024
#ifndef NO_SHA
2025
    printf("\tsizeof SHA          = %lu\n", (unsigned long)sizeof(wc_Sha));
2026
#endif
2027
#ifdef WOLFSSL_SHA224
2028
    printf("\tsizeof SHA224       = %lu\n", (unsigned long)sizeof(wc_Sha224));
2029
#endif
2030
#ifndef NO_SHA256
2031
    printf("\tsizeof SHA256       = %lu\n", (unsigned long)sizeof(wc_Sha256));
2032
#endif
2033
#ifdef WOLFSSL_SHA384
2034
    printf("\tsizeof SHA384       = %lu\n", (unsigned long)sizeof(wc_Sha384));
2035
#endif
2036
#ifdef WOLFSSL_SHA384
2037
    printf("\tsizeof SHA512       = %lu\n", (unsigned long)sizeof(wc_Sha512));
2038
#endif
2039
#ifdef WOLFSSL_SM3
2040
    printf("\tsizeof sm3          = %lu\n", (unsigned long)sizeof(Sm3));
2041
#endif
2042
    printf("sizeof Buffers          = %lu\n", (unsigned long)sizeof(Buffers));
2043
    printf("sizeof Options          = %lu\n", (unsigned long)sizeof(Options));
2044
    printf("sizeof Arrays           = %lu\n", (unsigned long)sizeof(Arrays));
2045
#ifndef NO_RSA
2046
    printf("sizeof RsaKey           = %lu\n", (unsigned long)sizeof(RsaKey));
2047
#endif
2048
#ifdef HAVE_ECC
2049
    printf("sizeof ecc_key          = %lu\n", (unsigned long)sizeof(ecc_key));
2050
#endif
2051
    printf("sizeof WOLFSSL_CIPHER    = %lu\n", (unsigned long)
2052
        sizeof(WOLFSSL_CIPHER));
2053
    printf("sizeof WOLFSSL_SESSION   = %lu\n", (unsigned long)
2054
        sizeof(WOLFSSL_SESSION));
2055
    printf("sizeof WOLFSSL           = %lu\n", (unsigned long)sizeof(WOLFSSL));
2056
    printf("sizeof WOLFSSL_CTX       = %lu\n", (unsigned long)
2057
        sizeof(WOLFSSL_CTX));
2058
#endif
2059
2060
0
    return sizeof(WOLFSSL);
2061
0
}
2062
2063
int wolfSSL_CTX_GetObjectSize(void)
2064
0
{
2065
0
    return sizeof(WOLFSSL_CTX);
2066
0
}
2067
2068
int wolfSSL_METHOD_GetObjectSize(void)
2069
0
{
2070
0
    return sizeof(WOLFSSL_METHOD);
2071
0
}
2072
#endif
2073
2074
2075
#ifdef WOLFSSL_STATIC_MEMORY
2076
2077
int wolfSSL_CTX_load_static_memory(WOLFSSL_CTX** ctx,
2078
    wolfSSL_method_func method, unsigned char* buf, unsigned int sz, int flag,
2079
    int maxSz)
2080
{
2081
    WOLFSSL_HEAP_HINT* hint = NULL;
2082
2083
    if (ctx == NULL || buf == NULL) {
2084
        return BAD_FUNC_ARG;
2085
    }
2086
2087
    if (*ctx == NULL && method == NULL) {
2088
        return BAD_FUNC_ARG;
2089
    }
2090
2091
    /* If there is a heap already, capture it in hint. */
2092
    if (*ctx && (*ctx)->heap != NULL) {
2093
        hint = (*ctx)->heap;
2094
    }
2095
2096
    if (wc_LoadStaticMemory(&hint, buf, sz, flag, maxSz)) {
2097
        WOLFSSL_MSG("Error loading static memory");
2098
        return WOLFSSL_FAILURE;
2099
    }
2100
2101
    if (*ctx) {
2102
        if ((*ctx)->heap == NULL) {
2103
            (*ctx)->heap = (void*)hint;
2104
        }
2105
    }
2106
    else {
2107
        /* create ctx if needed */
2108
        *ctx = wolfSSL_CTX_new_ex(method(hint), hint);
2109
        if (*ctx == NULL) {
2110
            WOLFSSL_MSG("Error creating ctx");
2111
            return WOLFSSL_FAILURE;
2112
        }
2113
    }
2114
2115
    return WOLFSSL_SUCCESS;
2116
}
2117
2118
2119
int wolfSSL_is_static_memory(WOLFSSL* ssl, WOLFSSL_MEM_CONN_STATS* mem_stats)
2120
{
2121
    if (ssl == NULL) {
2122
        return BAD_FUNC_ARG;
2123
    }
2124
    WOLFSSL_ENTER("wolfSSL_is_static_memory");
2125
2126
#ifndef WOLFSSL_STATIC_MEMORY_LEAN
2127
    /* fill out statistics if wanted and WOLFMEM_TRACK_STATS flag */
2128
    if (mem_stats != NULL && ssl->heap != NULL) {
2129
        WOLFSSL_HEAP_HINT* hint = ((WOLFSSL_HEAP_HINT*)(ssl->heap));
2130
        WOLFSSL_HEAP* heap      = hint->memory;
2131
        if (heap->flag & WOLFMEM_TRACK_STATS && hint->stats != NULL) {
2132
            XMEMCPY(mem_stats, hint->stats, sizeof(WOLFSSL_MEM_CONN_STATS));
2133
        }
2134
    }
2135
#endif
2136
2137
    (void)mem_stats;
2138
    return (ssl->heap) ? 1 : 0;
2139
}
2140
2141
2142
int wolfSSL_CTX_is_static_memory(WOLFSSL_CTX* ctx, WOLFSSL_MEM_STATS* mem_stats)
2143
{
2144
    if (ctx == NULL) {
2145
        return BAD_FUNC_ARG;
2146
    }
2147
    WOLFSSL_ENTER("wolfSSL_CTX_is_static_memory");
2148
2149
#ifndef WOLFSSL_STATIC_MEMORY_LEAN
2150
    /* fill out statistics if wanted */
2151
    if (mem_stats != NULL && ctx->heap != NULL) {
2152
        WOLFSSL_HEAP* heap = ((WOLFSSL_HEAP_HINT*)(ctx->heap))->memory;
2153
        if (wolfSSL_GetMemStats(heap, mem_stats) != 1) {
2154
            return MEMORY_E;
2155
        }
2156
    }
2157
#endif
2158
2159
    (void)mem_stats;
2160
    return (ctx->heap) ? 1 : 0;
2161
}
2162
2163
#endif /* WOLFSSL_STATIC_MEMORY */
2164
2165
#ifndef NO_TLS
2166
/* return max record layer size plaintext input size */
2167
int wolfSSL_GetMaxOutputSize(WOLFSSL* ssl)
2168
0
{
2169
0
    WOLFSSL_ENTER("wolfSSL_GetMaxOutputSize");
2170
2171
0
    if (ssl == NULL)
2172
0
        return BAD_FUNC_ARG;
2173
2174
0
    if (ssl->options.handShakeState != HANDSHAKE_DONE) {
2175
0
        WOLFSSL_MSG("Handshake not complete yet");
2176
0
        return BAD_FUNC_ARG;
2177
0
    }
2178
2179
0
    return min(OUTPUT_RECORD_SIZE, wolfssl_local_GetMaxPlaintextSize(ssl));
2180
0
}
2181
2182
2183
/* return record layer size of plaintext input size */
2184
int wolfSSL_GetOutputSize(WOLFSSL* ssl, int inSz)
2185
0
{
2186
0
    int maxSize;
2187
2188
0
    WOLFSSL_ENTER("wolfSSL_GetOutputSize");
2189
2190
0
    if (inSz < 0)
2191
0
        return BAD_FUNC_ARG;
2192
2193
0
    maxSize = wolfSSL_GetMaxOutputSize(ssl);
2194
0
    if (maxSize < 0)
2195
0
        return maxSize;   /* error */
2196
0
    if (inSz > maxSize)
2197
0
        return INPUT_SIZE_E;
2198
2199
0
    return wolfssl_local_GetRecordSize(ssl, inSz, 1);
2200
0
}
2201
2202
2203
#ifdef HAVE_ECC
2204
int wolfSSL_CTX_SetMinEccKey_Sz(WOLFSSL_CTX* ctx, short keySz)
2205
0
{
2206
0
    short keySzBytes;
2207
2208
0
    WOLFSSL_ENTER("wolfSSL_CTX_SetMinEccKey_Sz");
2209
0
    if (ctx == NULL || keySz < 0) {
2210
0
        WOLFSSL_MSG("Key size must be positive value or ctx was null");
2211
0
        return BAD_FUNC_ARG;
2212
0
    }
2213
2214
0
    if (keySz % 8 == 0) {
2215
0
        keySzBytes = keySz / 8;
2216
0
    }
2217
0
    else {
2218
0
        keySzBytes = (keySz / 8) + 1;
2219
0
    }
2220
2221
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2222
    if (crypto_policy.enabled) {
2223
        if (ctx->minEccKeySz > (keySzBytes)) {
2224
            return CRYPTO_POLICY_FORBIDDEN;
2225
        }
2226
    }
2227
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2228
2229
0
    ctx->minEccKeySz     = keySzBytes;
2230
0
#ifndef NO_CERTS
2231
0
    ctx->cm->minEccKeySz = keySzBytes;
2232
0
#endif
2233
0
    return WOLFSSL_SUCCESS;
2234
0
}
2235
2236
2237
int wolfSSL_SetMinEccKey_Sz(WOLFSSL* ssl, short keySz)
2238
0
{
2239
0
    short keySzBytes;
2240
2241
0
    WOLFSSL_ENTER("wolfSSL_SetMinEccKey_Sz");
2242
0
    if (ssl == NULL || keySz < 0) {
2243
0
        WOLFSSL_MSG("Key size must be positive value or ctx was null");
2244
0
        return BAD_FUNC_ARG;
2245
0
    }
2246
2247
0
    if (keySz % 8 == 0) {
2248
0
        keySzBytes = keySz / 8;
2249
0
    }
2250
0
    else {
2251
0
        keySzBytes = (keySz / 8) + 1;
2252
0
    }
2253
2254
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2255
    if (crypto_policy.enabled) {
2256
        if (ssl->options.minEccKeySz > (keySzBytes)) {
2257
            return CRYPTO_POLICY_FORBIDDEN;
2258
        }
2259
    }
2260
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2261
2262
0
    ssl->options.minEccKeySz = keySzBytes;
2263
0
    return WOLFSSL_SUCCESS;
2264
0
}
2265
2266
#endif /* HAVE_ECC */
2267
2268
#ifndef NO_RSA
2269
int wolfSSL_CTX_SetMinRsaKey_Sz(WOLFSSL_CTX* ctx, short keySz)
2270
0
{
2271
0
    if (ctx == NULL || keySz < 0 || keySz % 8 != 0) {
2272
0
        WOLFSSL_MSG("Key size must be divisible by 8 or ctx was null");
2273
0
        return BAD_FUNC_ARG;
2274
0
    }
2275
2276
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2277
    if (crypto_policy.enabled) {
2278
        if (ctx->minRsaKeySz > (keySz / 8)) {
2279
            return CRYPTO_POLICY_FORBIDDEN;
2280
        }
2281
    }
2282
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2283
2284
0
    ctx->minRsaKeySz     = keySz / 8;
2285
0
    ctx->cm->minRsaKeySz = keySz / 8;
2286
0
    return WOLFSSL_SUCCESS;
2287
0
}
2288
2289
2290
int wolfSSL_SetMinRsaKey_Sz(WOLFSSL* ssl, short keySz)
2291
0
{
2292
0
    if (ssl == NULL || keySz < 0 || keySz % 8 != 0) {
2293
0
        WOLFSSL_MSG("Key size must be divisible by 8 or ssl was null");
2294
0
        return BAD_FUNC_ARG;
2295
0
    }
2296
2297
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2298
    if (crypto_policy.enabled) {
2299
        if (ssl->options.minRsaKeySz > (keySz / 8)) {
2300
            return CRYPTO_POLICY_FORBIDDEN;
2301
        }
2302
    }
2303
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2304
2305
0
    ssl->options.minRsaKeySz = keySz / 8;
2306
0
    return WOLFSSL_SUCCESS;
2307
0
}
2308
#endif /* !NO_RSA */
2309
2310
#ifndef NO_DH
2311
2312
#if !defined(WOLFSSL_OLD_PRIME_CHECK) && !defined(HAVE_FIPS) && \
2313
    !defined(HAVE_SELFTEST)
2314
/* Enables or disables the session's DH key prime test. */
2315
int wolfSSL_SetEnableDhKeyTest(WOLFSSL* ssl, int enable)
2316
0
{
2317
0
    WOLFSSL_ENTER("wolfSSL_SetEnableDhKeyTest");
2318
2319
0
    if (ssl == NULL)
2320
0
        return BAD_FUNC_ARG;
2321
2322
0
    if (!enable)
2323
0
        ssl->options.dhDoKeyTest = 0;
2324
0
    else
2325
0
        ssl->options.dhDoKeyTest = 1;
2326
2327
0
    WOLFSSL_LEAVE("wolfSSL_SetEnableDhKeyTest", WOLFSSL_SUCCESS);
2328
0
    return WOLFSSL_SUCCESS;
2329
0
}
2330
#endif
2331
2332
int wolfSSL_CTX_SetMinDhKey_Sz(WOLFSSL_CTX* ctx, word16 keySz_bits)
2333
0
{
2334
0
    if (ctx == NULL || keySz_bits > 16000 || keySz_bits % 8 != 0)
2335
0
        return BAD_FUNC_ARG;
2336
2337
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2338
    if (crypto_policy.enabled) {
2339
        if (ctx->minDhKeySz > (keySz_bits / 8)) {
2340
            return CRYPTO_POLICY_FORBIDDEN;
2341
        }
2342
    }
2343
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2344
2345
0
    ctx->minDhKeySz = keySz_bits / 8;
2346
0
    return WOLFSSL_SUCCESS;
2347
0
}
2348
2349
2350
int wolfSSL_SetMinDhKey_Sz(WOLFSSL* ssl, word16 keySz_bits)
2351
0
{
2352
0
    if (ssl == NULL || keySz_bits > 16000 || keySz_bits % 8 != 0)
2353
0
        return BAD_FUNC_ARG;
2354
2355
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2356
    if (crypto_policy.enabled) {
2357
        if (ssl->options.minDhKeySz > (keySz_bits / 8)) {
2358
            return CRYPTO_POLICY_FORBIDDEN;
2359
        }
2360
    }
2361
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2362
2363
0
    ssl->options.minDhKeySz = keySz_bits / 8;
2364
0
    return WOLFSSL_SUCCESS;
2365
0
}
2366
2367
2368
int wolfSSL_CTX_SetMaxDhKey_Sz(WOLFSSL_CTX* ctx, word16 keySz_bits)
2369
0
{
2370
0
    if (ctx == NULL || keySz_bits > 16000 || keySz_bits % 8 != 0)
2371
0
        return BAD_FUNC_ARG;
2372
2373
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2374
    if (crypto_policy.enabled) {
2375
        if (ctx->minDhKeySz > (keySz_bits / 8)) {
2376
            return CRYPTO_POLICY_FORBIDDEN;
2377
        }
2378
    }
2379
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2380
2381
0
    ctx->maxDhKeySz = keySz_bits / 8;
2382
0
    return WOLFSSL_SUCCESS;
2383
0
}
2384
2385
2386
int wolfSSL_SetMaxDhKey_Sz(WOLFSSL* ssl, word16 keySz_bits)
2387
0
{
2388
0
    if (ssl == NULL || keySz_bits > 16000 || keySz_bits % 8 != 0)
2389
0
        return BAD_FUNC_ARG;
2390
2391
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
2392
    if (crypto_policy.enabled) {
2393
        if (ssl->options.minDhKeySz > (keySz_bits / 8)) {
2394
            return CRYPTO_POLICY_FORBIDDEN;
2395
        }
2396
    }
2397
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
2398
2399
0
    ssl->options.maxDhKeySz = keySz_bits / 8;
2400
0
    return WOLFSSL_SUCCESS;
2401
0
}
2402
2403
2404
int wolfSSL_GetDhKey_Sz(WOLFSSL* ssl)
2405
0
{
2406
0
    if (ssl == NULL)
2407
0
        return BAD_FUNC_ARG;
2408
2409
0
    return (ssl->options.dhKeySz * 8);
2410
0
}
2411
2412
#endif /* !NO_DH */
2413
2414
2415
static int wolfSSL_write_internal(WOLFSSL* ssl, const void* data, size_t sz)
2416
{
2417
    int ret;
2418
2419
    WOLFSSL_ENTER("wolfSSL_write");
2420
2421
    if (ssl == NULL || data == NULL)
2422
        return BAD_FUNC_ARG;
2423
2424
#ifdef WOLFSSL_QUIC
2425
    if (WOLFSSL_IS_QUIC(ssl)) {
2426
        WOLFSSL_MSG("SSL_write() on QUIC not allowed");
2427
        return BAD_FUNC_ARG;
2428
    }
2429
#endif
2430
2431
#ifdef HAVE_WRITE_DUP
2432
    { /* local variable scope */
2433
        int dupErr = 0;   /* local copy */
2434
2435
        ret = 0;
2436
2437
        if (ssl->dupWrite && ssl->dupSide == READ_DUP_SIDE) {
2438
            WOLFSSL_MSG("Read dup side cannot write");
2439
            return WRITE_DUP_WRITE_E;
2440
        }
2441
        if (ssl->dupWrite) {
2442
            if (wc_LockMutex(&ssl->dupWrite->dupMutex) != 0) {
2443
                return BAD_MUTEX_E;
2444
            }
2445
            dupErr = ssl->dupWrite->dupErr;
2446
            ret = wc_UnLockMutex(&ssl->dupWrite->dupMutex);
2447
        }
2448
2449
        if (ret != 0) {
2450
            ssl->error = ret;  /* high priority fatal error */
2451
            return WOLFSSL_FATAL_ERROR;
2452
        }
2453
        if (dupErr != 0) {
2454
            WOLFSSL_MSG("Write dup error from other side");
2455
            ssl->error = dupErr;
2456
            return WOLFSSL_FATAL_ERROR;
2457
        }
2458
    }
2459
#endif
2460
2461
#ifdef HAVE_ERRNO_H
2462
    errno = 0;
2463
#endif
2464
2465
    #ifdef OPENSSL_EXTRA
2466
    if (ssl->CBIS != NULL) {
2467
        ssl->CBIS(ssl, WOLFSSL_CB_WRITE, WOLFSSL_SUCCESS);
2468
        ssl->cbmode = WOLFSSL_CB_WRITE;
2469
    }
2470
    #endif
2471
    ret = SendData(ssl, data, sz);
2472
2473
    WOLFSSL_LEAVE("wolfSSL_write", ret);
2474
2475
    if (ret < 0)
2476
        return WOLFSSL_FATAL_ERROR;
2477
    else
2478
        return ret;
2479
}
2480
2481
WOLFSSL_ABI
2482
int wolfSSL_write(WOLFSSL* ssl, const void* data, int sz)
2483
249
{
2484
249
    WOLFSSL_ENTER("wolfSSL_write");
2485
2486
249
    if (sz < 0)
2487
0
        return BAD_FUNC_ARG;
2488
2489
249
    return wolfSSL_write_internal(ssl, data, (size_t)sz);
2490
249
}
2491
2492
int wolfSSL_inject(WOLFSSL* ssl, const void* data, int sz)
2493
0
{
2494
0
    int maxLength;
2495
0
    int usedLength;
2496
2497
0
    WOLFSSL_ENTER("wolfSSL_inject");
2498
2499
0
    if (ssl == NULL || data == NULL || sz <= 0)
2500
0
        return BAD_FUNC_ARG;
2501
2502
0
    usedLength = (int)(ssl->buffers.inputBuffer.length -
2503
0
                       ssl->buffers.inputBuffer.idx);
2504
0
    maxLength  = (int)(ssl->buffers.inputBuffer.bufferSize -
2505
0
                       (word32)usedLength);
2506
2507
0
    if (sz > maxLength) {
2508
        /* Need to make space */
2509
0
        int ret;
2510
0
        if (ssl->buffers.clearOutputBuffer.length > 0) {
2511
            /* clearOutputBuffer points into so reallocating inputBuffer will
2512
             * invalidate clearOutputBuffer and lose app data */
2513
0
            WOLFSSL_MSG("Can't inject while there is application data to read");
2514
0
            return APP_DATA_READY;
2515
0
        }
2516
0
        ret = GrowInputBuffer(ssl, sz, usedLength);
2517
0
        if (ret < 0)
2518
0
            return ret;
2519
0
    }
2520
2521
0
    XMEMCPY(ssl->buffers.inputBuffer.buffer + ssl->buffers.inputBuffer.idx,
2522
0
            data, sz);
2523
0
    ssl->buffers.inputBuffer.length += sz;
2524
2525
0
    return WOLFSSL_SUCCESS;
2526
0
}
2527
2528
2529
int wolfSSL_write_ex(WOLFSSL* ssl, const void* data, size_t sz, size_t* wr)
2530
0
{
2531
0
    int ret;
2532
2533
0
    if (wr != NULL) {
2534
0
        *wr = 0;
2535
0
    }
2536
2537
0
    ret = wolfSSL_write_internal(ssl, data, sz);
2538
0
    if (ret >= 0) {
2539
0
        if (wr != NULL) {
2540
0
            *wr = (size_t)ret;
2541
0
        }
2542
2543
        /* handle partial write cases, if not set then a partial write is
2544
         * considered a failure case, or if set and ret is 0 then is a fail */
2545
0
        if (ret == 0 && ssl->options.partialWrite) {
2546
0
            ret = 0;
2547
0
        }
2548
0
        else if ((size_t)ret < sz && !ssl->options.partialWrite) {
2549
0
            ret = 0;
2550
0
        }
2551
0
        else {
2552
            /* wrote out all application data, or wrote out 1 byte or more with
2553
             * partial write flag set */
2554
0
            ret = 1;
2555
0
        }
2556
0
    }
2557
0
    else {
2558
0
        ret = 0;
2559
0
    }
2560
2561
0
    return ret;
2562
0
}
2563
2564
2565
static int wolfSSL_read_internal(WOLFSSL* ssl, void* data, size_t sz, int peek)
2566
0
{
2567
0
    int ret;
2568
2569
0
    WOLFSSL_ENTER("wolfSSL_read_internal");
2570
2571
0
    if (ssl == NULL || data == NULL)
2572
0
        return BAD_FUNC_ARG;
2573
2574
#ifdef WOLFSSL_QUIC
2575
    if (WOLFSSL_IS_QUIC(ssl)) {
2576
        WOLFSSL_MSG("SSL_read() on QUIC not allowed");
2577
        return BAD_FUNC_ARG;
2578
    }
2579
#endif
2580
0
#if defined(WOLFSSL_ERROR_CODE_OPENSSL) && defined(OPENSSL_EXTRA)
2581
    /* This additional logic is meant to simulate following openSSL behavior:
2582
     * After bidirectional SSL_shutdown complete, SSL_read returns 0 and
2583
     * SSL_get_error_code returns SSL_ERROR_ZERO_RETURN.
2584
     * This behavior is used to know the disconnect of the underlying
2585
     * transport layer.
2586
     *
2587
     * In this logic, CBIORecv is called with a read size of 0 to check the
2588
     * transport layer status. It also returns WOLFSSL_FAILURE so that
2589
     * SSL_read does not return a positive number on failure.
2590
     */
2591
2592
    /* make sure bidirectional TLS shutdown completes */
2593
0
    if (ssl->error == WOLFSSL_ERROR_SYSCALL || ssl->options.shutdownDone) {
2594
        /* ask the underlying transport the connection is closed */
2595
0
        if (ssl->CBIORecv(ssl, (char*)data, 0, ssl->IOCB_ReadCtx)
2596
0
            == WC_NO_ERR_TRACE(WOLFSSL_CBIO_ERR_CONN_CLOSE))
2597
0
        {
2598
0
            ssl->options.isClosed = 1;
2599
0
            ssl->error = WOLFSSL_ERROR_ZERO_RETURN;
2600
0
        }
2601
0
        return WOLFSSL_FAILURE;
2602
0
    }
2603
0
#endif
2604
2605
#ifdef HAVE_WRITE_DUP
2606
    if (ssl->dupWrite && ssl->dupSide == WRITE_DUP_SIDE) {
2607
        WOLFSSL_MSG("Write dup side cannot read");
2608
        return WRITE_DUP_READ_E;
2609
    }
2610
#endif
2611
2612
0
#ifdef HAVE_ERRNO_H
2613
0
        errno = 0;
2614
0
#endif
2615
2616
0
    ret = ReceiveData(ssl, (byte*)data, sz, peek);
2617
2618
#ifdef HAVE_WRITE_DUP
2619
    if (ssl->dupWrite) {
2620
        if (ssl->error != 0 && ssl->error != WC_NO_ERR_TRACE(WANT_READ)
2621
        #ifdef WOLFSSL_ASYNC_CRYPT
2622
            && ssl->error != WC_NO_ERR_TRACE(WC_PENDING_E)
2623
        #endif
2624
        ) {
2625
            int notifyErr;
2626
2627
            WOLFSSL_MSG("Notifying write side of fatal read error");
2628
            notifyErr  = NotifyWriteSide(ssl, ssl->error);
2629
            if (notifyErr < 0) {
2630
                ret = ssl->error = notifyErr;
2631
            }
2632
        }
2633
    }
2634
#endif
2635
2636
0
    WOLFSSL_LEAVE("wolfSSL_read_internal", ret);
2637
2638
0
    if (ret < 0)
2639
0
        return WOLFSSL_FATAL_ERROR;
2640
0
    else
2641
0
        return ret;
2642
0
}
2643
2644
2645
int wolfSSL_peek(WOLFSSL* ssl, void* data, int sz)
2646
0
{
2647
0
    WOLFSSL_ENTER("wolfSSL_peek");
2648
2649
0
    if (sz < 0)
2650
0
        return BAD_FUNC_ARG;
2651
2652
0
    return wolfSSL_read_internal(ssl, data, (size_t)sz, TRUE);
2653
0
}
2654
2655
2656
WOLFSSL_ABI
2657
int wolfSSL_read(WOLFSSL* ssl, void* data, int sz)
2658
249
{
2659
249
    WOLFSSL_ENTER("wolfSSL_read");
2660
2661
249
    if (sz < 0)
2662
0
        return BAD_FUNC_ARG;
2663
2664
249
    #ifdef OPENSSL_EXTRA
2665
249
    if (ssl == NULL) {
2666
0
        return BAD_FUNC_ARG;
2667
0
    }
2668
249
    if (ssl->CBIS != NULL) {
2669
0
        ssl->CBIS(ssl, WOLFSSL_CB_READ, WOLFSSL_SUCCESS);
2670
0
        ssl->cbmode = WOLFSSL_CB_READ;
2671
0
    }
2672
249
    #endif
2673
249
    return wolfSSL_read_internal(ssl, data, (size_t)sz, FALSE);
2674
249
}
2675
2676
2677
/* returns 0 on failure and 1 on read */
2678
int wolfSSL_read_ex(WOLFSSL* ssl, void* data, size_t sz, size_t* rd)
2679
0
{
2680
0
    int ret;
2681
2682
0
    #ifdef OPENSSL_EXTRA
2683
0
    if (ssl == NULL) {
2684
0
        return BAD_FUNC_ARG;
2685
0
    }
2686
0
    if (ssl->CBIS != NULL) {
2687
0
        ssl->CBIS(ssl, WOLFSSL_CB_READ, WOLFSSL_SUCCESS);
2688
0
        ssl->cbmode = WOLFSSL_CB_READ;
2689
0
    }
2690
0
    #endif
2691
0
    ret = wolfSSL_read_internal(ssl, data, sz, FALSE);
2692
2693
0
    if (ret > 0 && rd != NULL) {
2694
0
        *rd = (size_t)ret;
2695
0
    }
2696
2697
0
    return ret > 0 ? 1 : 0;
2698
0
}
2699
2700
#ifdef WOLFSSL_MULTICAST
2701
2702
int wolfSSL_mcast_read(WOLFSSL* ssl, word16* id, void* data, int sz)
2703
{
2704
    int ret = 0;
2705
2706
    WOLFSSL_ENTER("wolfSSL_mcast_read");
2707
2708
    if ((ssl == NULL) || (sz < 0))
2709
        return BAD_FUNC_ARG;
2710
2711
    ret = wolfSSL_read_internal(ssl, data, (size_t)sz, FALSE);
2712
    if (ssl->options.dtls && ssl->options.haveMcast && id != NULL)
2713
        *id = ssl->keys.curPeerId;
2714
    return ret;
2715
}
2716
2717
#endif /* WOLFSSL_MULTICAST */
2718
#endif /* !NO_TLS */
2719
2720
/* helpers to set the device id, WOLFSSL_SUCCESS on ok */
2721
WOLFSSL_ABI
2722
int wolfSSL_SetDevId(WOLFSSL* ssl, int devId)
2723
0
{
2724
0
    if (ssl == NULL)
2725
0
        return BAD_FUNC_ARG;
2726
2727
0
    ssl->devId = devId;
2728
2729
0
    return WOLFSSL_SUCCESS;
2730
0
}
2731
2732
WOLFSSL_ABI
2733
int wolfSSL_CTX_SetDevId(WOLFSSL_CTX* ctx, int devId)
2734
0
{
2735
0
    if (ctx == NULL)
2736
0
        return BAD_FUNC_ARG;
2737
2738
0
    ctx->devId = devId;
2739
2740
0
    return WOLFSSL_SUCCESS;
2741
0
}
2742
2743
/* helpers to get device id and heap */
2744
WOLFSSL_ABI
2745
int wolfSSL_CTX_GetDevId(WOLFSSL_CTX* ctx, WOLFSSL* ssl)
2746
40
{
2747
40
    int devId = INVALID_DEVID;
2748
40
    if (ssl != NULL)
2749
0
        devId = ssl->devId;
2750
40
    if (ctx != NULL && devId == INVALID_DEVID)
2751
40
        devId = ctx->devId;
2752
40
    return devId;
2753
40
}
2754
void* wolfSSL_CTX_GetHeap(WOLFSSL_CTX* ctx, WOLFSSL* ssl)
2755
0
{
2756
0
    void* heap = NULL;
2757
0
    if (ctx != NULL)
2758
0
        heap = ctx->heap;
2759
0
    else if (ssl != NULL)
2760
0
        heap = ssl->heap;
2761
0
    return heap;
2762
0
}
2763
2764
2765
#ifndef NO_TLS
2766
#ifdef HAVE_SNI
2767
2768
WOLFSSL_ABI
2769
int wolfSSL_UseSNI(WOLFSSL* ssl, byte type, const void* data, word16 size)
2770
0
{
2771
0
    if (ssl == NULL)
2772
0
        return BAD_FUNC_ARG;
2773
2774
0
    return TLSX_UseSNI(&ssl->extensions, type, data, size, ssl->heap);
2775
0
}
2776
2777
2778
WOLFSSL_ABI
2779
int wolfSSL_CTX_UseSNI(WOLFSSL_CTX* ctx, byte type, const void* data,
2780
                                                                    word16 size)
2781
28
{
2782
28
    if (ctx == NULL)
2783
0
        return BAD_FUNC_ARG;
2784
2785
28
    return TLSX_UseSNI(&ctx->extensions, type, data, size, ctx->heap);
2786
28
}
2787
2788
#ifndef NO_WOLFSSL_SERVER
2789
2790
void wolfSSL_SNI_SetOptions(WOLFSSL* ssl, byte type, byte options)
2791
0
{
2792
0
    if (ssl && ssl->extensions)
2793
0
        TLSX_SNI_SetOptions(ssl->extensions, type, options);
2794
0
}
2795
2796
2797
void wolfSSL_CTX_SNI_SetOptions(WOLFSSL_CTX* ctx, byte type, byte options)
2798
0
{
2799
0
    if (ctx && ctx->extensions)
2800
0
        TLSX_SNI_SetOptions(ctx->extensions, type, options);
2801
0
}
2802
2803
2804
byte wolfSSL_SNI_Status(WOLFSSL* ssl, byte type)
2805
0
{
2806
0
    return TLSX_SNI_Status(ssl ? ssl->extensions : NULL, type);
2807
0
}
2808
2809
2810
word16 wolfSSL_SNI_GetRequest(WOLFSSL* ssl, byte type, void** data)
2811
0
{
2812
0
    if (data)
2813
0
        *data = NULL;
2814
2815
0
    if (ssl && ssl->extensions)
2816
0
        return TLSX_SNI_GetRequest(ssl->extensions, type, data, 0);
2817
2818
0
    return 0;
2819
0
}
2820
2821
2822
int wolfSSL_SNI_GetFromBuffer(const byte* clientHello, word32 helloSz,
2823
                              byte type, byte* sni, word32* inOutSz)
2824
0
{
2825
0
    if (clientHello && helloSz > 0 && sni && inOutSz && *inOutSz > 0)
2826
0
        return TLSX_SNI_GetFromBuffer(clientHello, helloSz, type, sni, inOutSz);
2827
2828
0
    return BAD_FUNC_ARG;
2829
0
}
2830
2831
#endif /* !NO_WOLFSSL_SERVER */
2832
2833
#endif /* HAVE_SNI */
2834
2835
2836
#ifdef HAVE_TRUSTED_CA
2837
2838
int wolfSSL_UseTrustedCA(WOLFSSL* ssl, byte type,
2839
    const byte* certId, word32 certIdSz)
2840
{
2841
    if (ssl == NULL)
2842
        return BAD_FUNC_ARG;
2843
2844
    if (type == WOLFSSL_TRUSTED_CA_PRE_AGREED) {
2845
        if (certId != NULL || certIdSz != 0)
2846
            return BAD_FUNC_ARG;
2847
    }
2848
    else if (type == WOLFSSL_TRUSTED_CA_X509_NAME) {
2849
        if (certId == NULL || certIdSz == 0)
2850
            return BAD_FUNC_ARG;
2851
    }
2852
    #ifndef NO_SHA
2853
    else if (type == WOLFSSL_TRUSTED_CA_KEY_SHA1 ||
2854
            type == WOLFSSL_TRUSTED_CA_CERT_SHA1) {
2855
        if (certId == NULL || certIdSz != WC_SHA_DIGEST_SIZE)
2856
            return BAD_FUNC_ARG;
2857
    }
2858
    #endif
2859
    else
2860
        return BAD_FUNC_ARG;
2861
2862
    return TLSX_UseTrustedCA(&ssl->extensions,
2863
            type, certId, certIdSz, ssl->heap);
2864
}
2865
2866
#endif /* HAVE_TRUSTED_CA */
2867
2868
2869
#ifdef HAVE_MAX_FRAGMENT
2870
#ifndef NO_WOLFSSL_CLIENT
2871
2872
int wolfSSL_UseMaxFragment(WOLFSSL* ssl, byte mfl)
2873
{
2874
    if (ssl == NULL)
2875
        return BAD_FUNC_ARG;
2876
2877
#ifdef WOLFSSL_ALLOW_MAX_FRAGMENT_ADJUST
2878
    /* The following is a non-standard way to reconfigure the max packet size
2879
        post-handshake for wolfSSL_write/wolfSSL_read */
2880
    if (ssl->options.handShakeState == HANDSHAKE_DONE) {
2881
        switch (mfl) {
2882
            case WOLFSSL_MFL_2_8 : ssl->max_fragment =  256; break;
2883
            case WOLFSSL_MFL_2_9 : ssl->max_fragment =  512; break;
2884
            case WOLFSSL_MFL_2_10: ssl->max_fragment = 1024; break;
2885
            case WOLFSSL_MFL_2_11: ssl->max_fragment = 2048; break;
2886
            case WOLFSSL_MFL_2_12: ssl->max_fragment = 4096; break;
2887
            case WOLFSSL_MFL_2_13: ssl->max_fragment = 8192; break;
2888
            default: ssl->max_fragment = MAX_RECORD_SIZE; break;
2889
        }
2890
        return WOLFSSL_SUCCESS;
2891
    }
2892
#endif /* WOLFSSL_MAX_FRAGMENT_ADJUST */
2893
2894
    /* This call sets the max fragment TLS extension, which gets sent to server.
2895
        The server_hello response is what sets the `ssl->max_fragment` in
2896
        TLSX_MFL_Parse */
2897
    return TLSX_UseMaxFragment(&ssl->extensions, mfl, ssl->heap);
2898
}
2899
2900
2901
int wolfSSL_CTX_UseMaxFragment(WOLFSSL_CTX* ctx, byte mfl)
2902
{
2903
    if (ctx == NULL)
2904
        return BAD_FUNC_ARG;
2905
2906
    return TLSX_UseMaxFragment(&ctx->extensions, mfl, ctx->heap);
2907
}
2908
2909
#endif /* NO_WOLFSSL_CLIENT */
2910
#endif /* HAVE_MAX_FRAGMENT */
2911
2912
#ifdef HAVE_TRUNCATED_HMAC
2913
#ifndef NO_WOLFSSL_CLIENT
2914
2915
int wolfSSL_UseTruncatedHMAC(WOLFSSL* ssl)
2916
{
2917
    if (ssl == NULL)
2918
        return BAD_FUNC_ARG;
2919
2920
    return TLSX_UseTruncatedHMAC(&ssl->extensions, ssl->heap);
2921
}
2922
2923
2924
int wolfSSL_CTX_UseTruncatedHMAC(WOLFSSL_CTX* ctx)
2925
{
2926
    if (ctx == NULL)
2927
        return BAD_FUNC_ARG;
2928
2929
    return TLSX_UseTruncatedHMAC(&ctx->extensions, ctx->heap);
2930
}
2931
2932
#endif /* NO_WOLFSSL_CLIENT */
2933
#endif /* HAVE_TRUNCATED_HMAC */
2934
2935
/* Elliptic Curves */
2936
#if defined(HAVE_SUPPORTED_CURVES)
2937
2938
static int isValidCurveGroup(word16 name)
2939
0
{
2940
0
    switch (name) {
2941
0
        case WOLFSSL_ECC_SECP160K1:
2942
0
        case WOLFSSL_ECC_SECP160R1:
2943
0
        case WOLFSSL_ECC_SECP160R2:
2944
0
        case WOLFSSL_ECC_SECP192K1:
2945
0
        case WOLFSSL_ECC_SECP192R1:
2946
0
        case WOLFSSL_ECC_SECP224K1:
2947
0
        case WOLFSSL_ECC_SECP224R1:
2948
0
        case WOLFSSL_ECC_SECP256K1:
2949
0
        case WOLFSSL_ECC_SECP256R1:
2950
0
        case WOLFSSL_ECC_SECP384R1:
2951
0
        case WOLFSSL_ECC_SECP521R1:
2952
0
        case WOLFSSL_ECC_BRAINPOOLP256R1:
2953
0
        case WOLFSSL_ECC_BRAINPOOLP384R1:
2954
0
        case WOLFSSL_ECC_BRAINPOOLP512R1:
2955
0
        case WOLFSSL_ECC_SM2P256V1:
2956
0
        case WOLFSSL_ECC_X25519:
2957
0
        case WOLFSSL_ECC_X448:
2958
0
        case WOLFSSL_ECC_BRAINPOOLP256R1TLS13:
2959
0
        case WOLFSSL_ECC_BRAINPOOLP384R1TLS13:
2960
0
        case WOLFSSL_ECC_BRAINPOOLP512R1TLS13:
2961
2962
0
        case WOLFSSL_FFDHE_2048:
2963
0
        case WOLFSSL_FFDHE_3072:
2964
0
        case WOLFSSL_FFDHE_4096:
2965
0
        case WOLFSSL_FFDHE_6144:
2966
0
        case WOLFSSL_FFDHE_8192:
2967
2968
#ifdef WOLFSSL_HAVE_MLKEM
2969
#ifndef WOLFSSL_NO_ML_KEM
2970
        case WOLFSSL_ML_KEM_512:
2971
        case WOLFSSL_ML_KEM_768:
2972
        case WOLFSSL_ML_KEM_1024:
2973
    #if defined(WOLFSSL_WC_MLKEM) || defined(HAVE_LIBOQS)
2974
        case WOLFSSL_SECP256R1MLKEM512:
2975
        case WOLFSSL_SECP384R1MLKEM768:
2976
        case WOLFSSL_SECP521R1MLKEM1024:
2977
        case WOLFSSL_SECP384R1MLKEM1024:
2978
        case WOLFSSL_X25519MLKEM512:
2979
        case WOLFSSL_X448MLKEM768:
2980
        case WOLFSSL_X25519MLKEM768:
2981
        case WOLFSSL_SECP256R1MLKEM768:
2982
    #endif
2983
#endif /* !WOLFSSL_NO_ML_KEM */
2984
#ifdef WOLFSSL_MLKEM_KYBER
2985
        case WOLFSSL_KYBER_LEVEL1:
2986
        case WOLFSSL_KYBER_LEVEL3:
2987
        case WOLFSSL_KYBER_LEVEL5:
2988
    #if defined(WOLFSSL_WC_MLKEM) || defined(HAVE_LIBOQS)
2989
        case WOLFSSL_P256_KYBER_LEVEL1:
2990
        case WOLFSSL_P384_KYBER_LEVEL3:
2991
        case WOLFSSL_P521_KYBER_LEVEL5:
2992
        case WOLFSSL_X25519_KYBER_LEVEL1:
2993
        case WOLFSSL_X448_KYBER_LEVEL3:
2994
        case WOLFSSL_X25519_KYBER_LEVEL3:
2995
        case WOLFSSL_P256_KYBER_LEVEL3:
2996
    #endif
2997
#endif /* WOLFSSL_MLKEM_KYBER */
2998
#endif
2999
0
            return 1;
3000
3001
0
        default:
3002
0
            return 0;
3003
0
    }
3004
0
}
3005
3006
int wolfSSL_UseSupportedCurve(WOLFSSL* ssl, word16 name)
3007
0
{
3008
0
    if (ssl == NULL || !isValidCurveGroup(name))
3009
0
        return BAD_FUNC_ARG;
3010
3011
0
    ssl->options.userCurves = 1;
3012
#if defined(NO_TLS)
3013
    return WOLFSSL_FAILURE;
3014
#else
3015
0
    return TLSX_UseSupportedCurve(&ssl->extensions, name, ssl->heap);
3016
0
#endif /* NO_TLS */
3017
0
}
3018
3019
3020
int wolfSSL_CTX_UseSupportedCurve(WOLFSSL_CTX* ctx, word16 name)
3021
0
{
3022
0
    if (ctx == NULL || !isValidCurveGroup(name))
3023
0
        return BAD_FUNC_ARG;
3024
3025
0
    ctx->userCurves = 1;
3026
#if defined(NO_TLS)
3027
    return WOLFSSL_FAILURE;
3028
#else
3029
0
    return TLSX_UseSupportedCurve(&ctx->extensions, name, ctx->heap);
3030
0
#endif /* NO_TLS */
3031
0
}
3032
3033
#if defined(OPENSSL_EXTRA)
3034
int  wolfSSL_CTX_set1_groups(WOLFSSL_CTX* ctx, int* groups,
3035
                                        int count)
3036
0
{
3037
0
    int i;
3038
0
    int _groups[WOLFSSL_MAX_GROUP_COUNT];
3039
0
    WOLFSSL_ENTER("wolfSSL_CTX_set1_groups");
3040
0
    if (count == 0) {
3041
0
        WOLFSSL_MSG("Group count is zero");
3042
0
        return WOLFSSL_FAILURE;
3043
0
    }
3044
0
    for (i = 0; i < count; i++) {
3045
0
        if (isValidCurveGroup((word16)groups[i])) {
3046
0
            _groups[i] = groups[i];
3047
0
        }
3048
0
#ifdef HAVE_ECC
3049
0
        else {
3050
            /* groups may be populated with curve NIDs */
3051
0
            int oid = (int)nid2oid(groups[i], oidCurveType);
3052
0
            int name = (int)GetCurveByOID(oid);
3053
0
            if (name == 0) {
3054
0
                WOLFSSL_MSG("Invalid group name");
3055
0
                return WOLFSSL_FAILURE;
3056
0
            }
3057
0
            _groups[i] = name;
3058
0
        }
3059
#else
3060
        else {
3061
            WOLFSSL_MSG("Invalid group name");
3062
            return WOLFSSL_FAILURE;
3063
        }
3064
#endif
3065
0
    }
3066
0
    return wolfSSL_CTX_set_groups(ctx, _groups, count) == WOLFSSL_SUCCESS ?
3067
0
            WOLFSSL_SUCCESS : WOLFSSL_FAILURE;
3068
0
}
3069
3070
int  wolfSSL_set1_groups(WOLFSSL* ssl, int* groups, int count)
3071
0
{
3072
0
    int i;
3073
0
    int _groups[WOLFSSL_MAX_GROUP_COUNT];
3074
0
    WOLFSSL_ENTER("wolfSSL_CTX_set1_groups");
3075
0
    if (count == 0) {
3076
0
        WOLFSSL_MSG("Group count is zero");
3077
0
        return WOLFSSL_FAILURE;
3078
0
    }
3079
0
    for (i = 0; i < count; i++) {
3080
0
        if (isValidCurveGroup((word16)groups[i])) {
3081
0
            _groups[i] = groups[i];
3082
0
        }
3083
0
#ifdef HAVE_ECC
3084
0
        else {
3085
            /* groups may be populated with curve NIDs */
3086
0
            int oid = (int)nid2oid(groups[i], oidCurveType);
3087
0
            int name = (int)GetCurveByOID(oid);
3088
0
            if (name == 0) {
3089
0
                WOLFSSL_MSG("Invalid group name");
3090
0
                return WOLFSSL_FAILURE;
3091
0
            }
3092
0
            _groups[i] = name;
3093
0
        }
3094
#else
3095
        else {
3096
            WOLFSSL_MSG("Invalid group name");
3097
            return WOLFSSL_FAILURE;
3098
        }
3099
#endif
3100
0
    }
3101
0
    return wolfSSL_set_groups(ssl, _groups, count) == WOLFSSL_SUCCESS ?
3102
0
            WOLFSSL_SUCCESS : WOLFSSL_FAILURE;
3103
0
}
3104
#endif /* OPENSSL_EXTRA */
3105
#endif /* HAVE_SUPPORTED_CURVES */
3106
3107
/* Application-Layer Protocol Negotiation */
3108
#ifdef HAVE_ALPN
3109
3110
WOLFSSL_ABI
3111
int wolfSSL_UseALPN(WOLFSSL* ssl, char *protocol_name_list,
3112
                    word32 protocol_name_listSz, byte options)
3113
{
3114
    char    *list, *ptr = NULL, **token;
3115
    word16  len;
3116
    int     idx = 0;
3117
    int     ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
3118
3119
    WOLFSSL_ENTER("wolfSSL_UseALPN");
3120
3121
    if (ssl == NULL || protocol_name_list == NULL)
3122
        return BAD_FUNC_ARG;
3123
3124
    if (protocol_name_listSz > (WOLFSSL_MAX_ALPN_NUMBER *
3125
                                WOLFSSL_MAX_ALPN_PROTO_NAME_LEN +
3126
                                WOLFSSL_MAX_ALPN_NUMBER)) {
3127
        WOLFSSL_MSG("Invalid arguments, protocol name list too long");
3128
        return BAD_FUNC_ARG;
3129
    }
3130
3131
    if (!(options & WOLFSSL_ALPN_CONTINUE_ON_MISMATCH) &&
3132
        !(options & WOLFSSL_ALPN_FAILED_ON_MISMATCH)) {
3133
            WOLFSSL_MSG("Invalid arguments, options not supported");
3134
            return BAD_FUNC_ARG;
3135
        }
3136
3137
3138
    list = (char *)XMALLOC(protocol_name_listSz+1, ssl->heap,
3139
                           DYNAMIC_TYPE_ALPN);
3140
    if (list == NULL) {
3141
        WOLFSSL_MSG("Memory failure");
3142
        return MEMORY_ERROR;
3143
    }
3144
3145
    token = (char **)XMALLOC(sizeof(char *) * (WOLFSSL_MAX_ALPN_NUMBER+1),
3146
        ssl->heap, DYNAMIC_TYPE_ALPN);
3147
    if (token == NULL) {
3148
        XFREE(list, ssl->heap, DYNAMIC_TYPE_ALPN);
3149
        WOLFSSL_MSG("Memory failure");
3150
        return MEMORY_ERROR;
3151
    }
3152
    XMEMSET(token, 0, sizeof(char *) * (WOLFSSL_MAX_ALPN_NUMBER+1));
3153
3154
    XSTRNCPY(list, protocol_name_list, protocol_name_listSz);
3155
    list[protocol_name_listSz] = '\0';
3156
3157
    /* read all protocol name from the list */
3158
    token[idx] = XSTRTOK(list, ",", &ptr);
3159
    while (idx < WOLFSSL_MAX_ALPN_NUMBER && token[idx] != NULL)
3160
        token[++idx] = XSTRTOK(NULL, ",", &ptr);
3161
3162
    /* add protocol name list in the TLS extension in reverse order */
3163
    while ((idx--) > 0) {
3164
        len = (word16)XSTRLEN(token[idx]);
3165
3166
        ret = TLSX_UseALPN(&ssl->extensions, token[idx], len, options,
3167
                                                                     ssl->heap);
3168
        if (ret != WOLFSSL_SUCCESS) {
3169
            WOLFSSL_MSG("TLSX_UseALPN failure");
3170
            break;
3171
        }
3172
    }
3173
3174
    XFREE(token, ssl->heap, DYNAMIC_TYPE_ALPN);
3175
    XFREE(list, ssl->heap, DYNAMIC_TYPE_ALPN);
3176
3177
    return ret;
3178
}
3179
3180
int wolfSSL_ALPN_GetProtocol(WOLFSSL* ssl, char **protocol_name, word16 *size)
3181
{
3182
    return TLSX_ALPN_GetRequest(ssl ? ssl->extensions : NULL,
3183
                               (void **)protocol_name, size);
3184
}
3185
3186
int wolfSSL_ALPN_GetPeerProtocol(WOLFSSL* ssl, char **list, word16 *listSz)
3187
{
3188
    int i, len;
3189
    char *p;
3190
    byte *s;
3191
3192
    if (ssl == NULL || list == NULL || listSz == NULL)
3193
        return BAD_FUNC_ARG;
3194
3195
    if (ssl->alpn_peer_requested == NULL
3196
        || ssl->alpn_peer_requested_length == 0)
3197
        return BUFFER_ERROR;
3198
3199
    /* ssl->alpn_peer_requested are the original bytes sent in a ClientHello,
3200
     * formatted as (len-byte chars+)+. To turn n protocols into a
3201
     * comma-separated C string, one needs (n-1) commas and a final 0 byte
3202
     * which has the same length as the original.
3203
     * The returned length is the strlen() of the C string, so -1 of that. */
3204
    *listSz = ssl->alpn_peer_requested_length-1;
3205
    *list = p = (char *)XMALLOC(ssl->alpn_peer_requested_length, ssl->heap,
3206
                                DYNAMIC_TYPE_TLSX);
3207
    if (p == NULL)
3208
        return MEMORY_ERROR;
3209
3210
    for (i = 0, s = ssl->alpn_peer_requested;
3211
         i < ssl->alpn_peer_requested_length;
3212
         p += len, i += len)
3213
    {
3214
        if (i)
3215
            *p++ = ',';
3216
        len = s[i++];
3217
        /* guard against bad length bytes. */
3218
        if (i + len > ssl->alpn_peer_requested_length) {
3219
            XFREE(*list, ssl->heap, DYNAMIC_TYPE_TLSX);
3220
            *list = NULL;
3221
            return WOLFSSL_FAILURE;
3222
        }
3223
        XMEMCPY(p, s + i, (size_t)len);
3224
    }
3225
    *p = 0;
3226
3227
    return WOLFSSL_SUCCESS;
3228
}
3229
3230
3231
/* used to free memory allocated by wolfSSL_ALPN_GetPeerProtocol */
3232
int wolfSSL_ALPN_FreePeerProtocol(WOLFSSL* ssl, char **list)
3233
{
3234
    if (ssl == NULL) {
3235
        return BAD_FUNC_ARG;
3236
    }
3237
3238
    XFREE(*list, ssl->heap, DYNAMIC_TYPE_TLSX);
3239
    *list = NULL;
3240
3241
    return WOLFSSL_SUCCESS;
3242
}
3243
3244
#endif /* HAVE_ALPN */
3245
3246
/* Secure Renegotiation */
3247
#ifdef HAVE_SERVER_RENEGOTIATION_INFO
3248
3249
/* user is forcing ability to use secure renegotiation, we discourage it */
3250
int wolfSSL_UseSecureRenegotiation(WOLFSSL* ssl)
3251
245
{
3252
245
    int ret = WC_NO_ERR_TRACE(BAD_FUNC_ARG);
3253
#if defined(NO_TLS)
3254
    (void)ssl;
3255
#else
3256
245
    if (ssl)
3257
245
        ret = TLSX_UseSecureRenegotiation(&ssl->extensions, ssl->heap);
3258
0
    else
3259
0
        ret = BAD_FUNC_ARG;
3260
3261
245
    if (ret == WOLFSSL_SUCCESS) {
3262
237
        TLSX* extension = TLSX_Find(ssl->extensions, TLSX_RENEGOTIATION_INFO);
3263
3264
237
        if (extension)
3265
237
            ssl->secure_renegotiation = (SecureRenegotiation*)extension->data;
3266
237
    }
3267
245
#endif /* !NO_TLS */
3268
245
    return ret;
3269
245
}
3270
3271
int wolfSSL_CTX_UseSecureRenegotiation(WOLFSSL_CTX* ctx)
3272
0
{
3273
0
    if (ctx == NULL)
3274
0
        return BAD_FUNC_ARG;
3275
3276
0
    ctx->useSecureReneg = 1;
3277
0
    return WOLFSSL_SUCCESS;
3278
0
}
3279
3280
#ifdef HAVE_SECURE_RENEGOTIATION
3281
/* do a secure renegotiation handshake, user forced, we discourage */
3282
static int _Rehandshake(WOLFSSL* ssl)
3283
{
3284
    int ret;
3285
3286
    if (ssl == NULL)
3287
        return BAD_FUNC_ARG;
3288
3289
    if (IsAtLeastTLSv1_3(ssl->version)) {
3290
        WOLFSSL_MSG("Secure Renegotiation not supported in TLS 1.3");
3291
        return SECURE_RENEGOTIATION_E;
3292
    }
3293
3294
    if (ssl->secure_renegotiation == NULL) {
3295
        WOLFSSL_MSG("Secure Renegotiation not forced on by user");
3296
        return SECURE_RENEGOTIATION_E;
3297
    }
3298
3299
    if (ssl->secure_renegotiation->enabled == 0) {
3300
        WOLFSSL_MSG("Secure Renegotiation not enabled at extension level");
3301
        return SECURE_RENEGOTIATION_E;
3302
    }
3303
3304
#ifdef WOLFSSL_DTLS
3305
    if (ssl->options.dtls && ssl->keys.dtls_epoch == 0xFFFF) {
3306
        WOLFSSL_MSG("Secure Renegotiation not allowed. Epoch would wrap");
3307
        return SECURE_RENEGOTIATION_E;
3308
    }
3309
#endif
3310
3311
    /* If the client started the renegotiation, the server will already
3312
     * have processed the client's hello. */
3313
    if (ssl->options.side != WOLFSSL_SERVER_END ||
3314
        ssl->options.acceptState != ACCEPT_FIRST_REPLY_DONE) {
3315
3316
        if (ssl->options.handShakeState != HANDSHAKE_DONE) {
3317
            if (!ssl->options.handShakeDone) {
3318
                WOLFSSL_MSG("Can't renegotiate until initial "
3319
                            "handshake complete");
3320
                return SECURE_RENEGOTIATION_E;
3321
            }
3322
            else {
3323
                WOLFSSL_MSG("Renegotiation already started. "
3324
                            "Moving it forward.");
3325
                ret = wolfSSL_negotiate(ssl);
3326
                if (ret == WOLFSSL_SUCCESS)
3327
                    ssl->secure_rene_count++;
3328
                return ret;
3329
            }
3330
        }
3331
3332
        /* reset handshake states */
3333
        ssl->options.sendVerify = 0;
3334
        ssl->options.serverState = NULL_STATE;
3335
        ssl->options.clientState = NULL_STATE;
3336
        ssl->options.connectState  = CONNECT_BEGIN;
3337
        ssl->options.acceptState   = ACCEPT_BEGIN_RENEG;
3338
        ssl->options.handShakeState = NULL_STATE;
3339
        ssl->options.processReply  = 0;  /* TODO, move states in internal.h */
3340
3341
        XMEMSET(&ssl->msgsReceived, 0, sizeof(ssl->msgsReceived));
3342
3343
        ssl->secure_renegotiation->cache_status = SCR_CACHE_NEEDED;
3344
3345
#if !defined(NO_WOLFSSL_SERVER) && !defined(WOLFSSL_NO_TLS12)
3346
        if (ssl->options.side == WOLFSSL_SERVER_END) {
3347
            ret = SendHelloRequest(ssl);
3348
            if (ret != 0) {
3349
                ssl->error = ret;
3350
                return WOLFSSL_FATAL_ERROR;
3351
            }
3352
        }
3353
#endif /* !NO_WOLFSSL_SERVER && !WOLFSSL_NO_TLS12 */
3354
3355
        ret = InitHandshakeHashes(ssl);
3356
        if (ret != 0) {
3357
            ssl->error = ret;
3358
            return WOLFSSL_FATAL_ERROR;
3359
        }
3360
    }
3361
    ret = wolfSSL_negotiate(ssl);
3362
    if (ret == WOLFSSL_SUCCESS)
3363
        ssl->secure_rene_count++;
3364
    return ret;
3365
}
3366
3367
3368
/* do a secure renegotiation handshake, user forced, we discourage */
3369
int wolfSSL_Rehandshake(WOLFSSL* ssl)
3370
{
3371
    int ret;
3372
    WOLFSSL_ENTER("wolfSSL_Rehandshake");
3373
3374
    if (ssl == NULL)
3375
        return WOLFSSL_FAILURE;
3376
3377
#ifdef HAVE_SESSION_TICKET
3378
    ret = WOLFSSL_SUCCESS;
3379
#endif
3380
3381
    if (ssl->options.side == WOLFSSL_SERVER_END) {
3382
        /* Reset option to send certificate verify. */
3383
        ssl->options.sendVerify = 0;
3384
        /* Reset resuming flag to do full secure handshake. */
3385
        ssl->options.resuming = 0;
3386
    }
3387
    else {
3388
        /* Reset resuming flag to do full secure handshake. */
3389
        ssl->options.resuming = 0;
3390
        #if defined(HAVE_SESSION_TICKET) && !defined(NO_WOLFSSL_CLIENT)
3391
            /* Clearing the ticket. */
3392
            ret = wolfSSL_UseSessionTicket(ssl);
3393
        #endif
3394
    }
3395
    /* CLIENT/SERVER: Reset peer authentication for full secure handshake. */
3396
    ssl->options.peerAuthGood = 0;
3397
3398
#ifdef HAVE_SESSION_TICKET
3399
    if (ret == WOLFSSL_SUCCESS)
3400
#endif
3401
        ret = _Rehandshake(ssl);
3402
3403
    return ret;
3404
}
3405
3406
3407
#ifndef NO_WOLFSSL_CLIENT
3408
3409
/* do a secure resumption handshake, user forced, we discourage */
3410
int wolfSSL_SecureResume(WOLFSSL* ssl)
3411
{
3412
    WOLFSSL_ENTER("wolfSSL_SecureResume");
3413
3414
    if (ssl == NULL)
3415
        return BAD_FUNC_ARG;
3416
3417
    if (ssl->options.side == WOLFSSL_SERVER_END) {
3418
        ssl->error = SIDE_ERROR;
3419
        return WOLFSSL_FATAL_ERROR;
3420
    }
3421
3422
    return _Rehandshake(ssl);
3423
}
3424
3425
#endif /* NO_WOLFSSL_CLIENT */
3426
3427
#endif /* HAVE_SECURE_RENEGOTIATION */
3428
3429
long wolfSSL_SSL_get_secure_renegotiation_support(WOLFSSL* ssl)
3430
0
{
3431
0
    WOLFSSL_ENTER("wolfSSL_SSL_get_secure_renegotiation_support");
3432
3433
0
    if (!ssl || !ssl->secure_renegotiation)
3434
0
        return WOLFSSL_FAILURE;
3435
0
    return ssl->secure_renegotiation->enabled;
3436
0
}
3437
3438
#endif /* HAVE_SECURE_RENEGOTIATION_INFO */
3439
3440
#if !defined(NO_WOLFSSL_CLIENT) && !defined(WOLFSSL_NO_TLS12) && \
3441
    defined(WOLFSSL_HARDEN_TLS) && !defined(WOLFSSL_HARDEN_TLS_NO_SCR_CHECK)
3442
WOLFSSL_API int wolfSSL_get_scr_check_enabled(const WOLFSSL* ssl)
3443
{
3444
    WOLFSSL_ENTER("wolfSSL_get_scr_check_enabled");
3445
3446
    if (ssl == NULL)
3447
        return BAD_FUNC_ARG;
3448
3449
    return ssl->scr_check_enabled;
3450
}
3451
3452
WOLFSSL_API int wolfSSL_set_scr_check_enabled(WOLFSSL* ssl, byte enabled)
3453
{
3454
    WOLFSSL_ENTER("wolfSSL_set_scr_check_enabled");
3455
3456
    if (ssl == NULL)
3457
        return BAD_FUNC_ARG;
3458
3459
    ssl->scr_check_enabled = !!enabled;
3460
    return WOLFSSL_SUCCESS;
3461
}
3462
#endif
3463
3464
#if defined(HAVE_SESSION_TICKET)
3465
/* Session Ticket */
3466
3467
#if !defined(NO_WOLFSSL_SERVER)
3468
int wolfSSL_CTX_NoTicketTLSv12(WOLFSSL_CTX* ctx)
3469
0
{
3470
0
    if (ctx == NULL)
3471
0
        return BAD_FUNC_ARG;
3472
3473
0
    ctx->noTicketTls12 = 1;
3474
3475
0
    return WOLFSSL_SUCCESS;
3476
0
}
3477
3478
int wolfSSL_NoTicketTLSv12(WOLFSSL* ssl)
3479
0
{
3480
0
    if (ssl == NULL)
3481
0
        return BAD_FUNC_ARG;
3482
3483
0
    ssl->options.noTicketTls12 = 1;
3484
3485
0
    return WOLFSSL_SUCCESS;
3486
0
}
3487
3488
/* WOLFSSL_SUCCESS on ok */
3489
int wolfSSL_CTX_set_TicketEncCb(WOLFSSL_CTX* ctx, SessionTicketEncCb cb)
3490
20
{
3491
20
    if (ctx == NULL)
3492
0
        return BAD_FUNC_ARG;
3493
3494
20
    ctx->ticketEncCb = cb;
3495
3496
20
    return WOLFSSL_SUCCESS;
3497
20
}
3498
3499
/* set hint interval, WOLFSSL_SUCCESS on ok */
3500
int wolfSSL_CTX_set_TicketHint(WOLFSSL_CTX* ctx, int hint)
3501
0
{
3502
0
    if (ctx == NULL)
3503
0
        return BAD_FUNC_ARG;
3504
3505
0
    ctx->ticketHint = hint;
3506
3507
0
    return WOLFSSL_SUCCESS;
3508
0
}
3509
3510
/* set user context, WOLFSSL_SUCCESS on ok */
3511
int wolfSSL_CTX_set_TicketEncCtx(WOLFSSL_CTX* ctx, void* userCtx)
3512
0
{
3513
0
    if (ctx == NULL)
3514
0
        return BAD_FUNC_ARG;
3515
3516
0
    ctx->ticketEncCtx = userCtx;
3517
3518
0
    return WOLFSSL_SUCCESS;
3519
0
}
3520
3521
/* get user context - returns userCtx on success, NULL on failure */
3522
void* wolfSSL_CTX_get_TicketEncCtx(WOLFSSL_CTX* ctx)
3523
0
{
3524
0
    if (ctx == NULL)
3525
0
        return NULL;
3526
3527
0
    return ctx->ticketEncCtx;
3528
0
}
3529
3530
#ifdef WOLFSSL_TLS13
3531
/* set the maximum number of tickets to send
3532
 * return WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE on fail
3533
 */
3534
int wolfSSL_CTX_set_num_tickets(WOLFSSL_CTX* ctx, size_t mxTickets)
3535
0
{
3536
0
    if (ctx == NULL)
3537
0
        return WOLFSSL_FAILURE;
3538
3539
0
    ctx->maxTicketTls13 = (unsigned int)mxTickets;
3540
0
    return WOLFSSL_SUCCESS;
3541
0
}
3542
3543
/* get the maximum number of tickets to send
3544
 * return number of tickets set to be sent
3545
 */
3546
size_t wolfSSL_CTX_get_num_tickets(WOLFSSL_CTX* ctx)
3547
0
{
3548
0
    if (ctx == NULL)
3549
0
        return 0;
3550
3551
0
    return (size_t)ctx->maxTicketTls13;
3552
0
}
3553
#endif /* WOLFSSL_TLS13 */
3554
#endif /* !NO_WOLFSSL_SERVER */
3555
3556
#if !defined(NO_WOLFSSL_CLIENT)
3557
int wolfSSL_UseSessionTicket(WOLFSSL* ssl)
3558
0
{
3559
0
    if (ssl == NULL)
3560
0
        return BAD_FUNC_ARG;
3561
3562
0
    return TLSX_UseSessionTicket(&ssl->extensions, NULL, ssl->heap);
3563
0
}
3564
3565
int wolfSSL_CTX_UseSessionTicket(WOLFSSL_CTX* ctx)
3566
28
{
3567
28
    if (ctx == NULL)
3568
0
        return BAD_FUNC_ARG;
3569
3570
28
    return TLSX_UseSessionTicket(&ctx->extensions, NULL, ctx->heap);
3571
28
}
3572
3573
int wolfSSL_get_SessionTicket(WOLFSSL* ssl, byte* buf, word32* bufSz)
3574
0
{
3575
0
    if (ssl == NULL || bufSz == NULL)
3576
0
        return BAD_FUNC_ARG;
3577
3578
0
    if (*bufSz == 0 && buf == NULL) {
3579
0
        *bufSz = ssl->session->ticketLen;
3580
0
        return LENGTH_ONLY_E;
3581
0
    }
3582
3583
0
    if (buf == NULL)
3584
0
        return BAD_FUNC_ARG;
3585
3586
0
    if (ssl->session->ticketLen <= *bufSz) {
3587
0
        XMEMCPY(buf, ssl->session->ticket, ssl->session->ticketLen);
3588
0
        *bufSz = ssl->session->ticketLen;
3589
0
    }
3590
0
    else
3591
0
        *bufSz = 0;
3592
3593
0
    return WOLFSSL_SUCCESS;
3594
0
}
3595
3596
int wolfSSL_set_SessionTicket(WOLFSSL* ssl, const byte* buf,
3597
                                          word32 bufSz)
3598
0
{
3599
0
    if (ssl == NULL || (buf == NULL && bufSz > 0))
3600
0
        return BAD_FUNC_ARG;
3601
3602
0
    if (bufSz > 0) {
3603
        /* Ticket will fit into static ticket */
3604
0
        if (bufSz <= SESSION_TICKET_LEN) {
3605
0
            if (ssl->session->ticketLenAlloc > 0) {
3606
0
                XFREE(ssl->session->ticket, ssl->session->heap,
3607
0
                      DYNAMIC_TYPE_SESSION_TICK);
3608
0
                ssl->session->ticketLenAlloc = 0;
3609
0
                ssl->session->ticket = ssl->session->staticTicket;
3610
0
            }
3611
0
        }
3612
0
        else { /* Ticket requires dynamic ticket storage */
3613
            /* is dyn buffer big enough */
3614
0
            if (ssl->session->ticketLen < bufSz) {
3615
0
                if (ssl->session->ticketLenAlloc > 0) {
3616
0
                    XFREE(ssl->session->ticket, ssl->session->heap,
3617
0
                          DYNAMIC_TYPE_SESSION_TICK);
3618
0
                }
3619
0
                ssl->session->ticket = (byte*)XMALLOC(bufSz, ssl->session->heap,
3620
0
                        DYNAMIC_TYPE_SESSION_TICK);
3621
0
                if(ssl->session->ticket == NULL) {
3622
0
                    ssl->session->ticket = ssl->session->staticTicket;
3623
0
                    ssl->session->ticketLenAlloc = 0;
3624
0
                    return MEMORY_ERROR;
3625
0
                }
3626
0
                ssl->session->ticketLenAlloc = (word16)bufSz;
3627
0
            }
3628
0
        }
3629
0
        XMEMCPY(ssl->session->ticket, buf, bufSz);
3630
0
    }
3631
0
    ssl->session->ticketLen = (word16)bufSz;
3632
3633
0
    return WOLFSSL_SUCCESS;
3634
0
}
3635
3636
3637
int wolfSSL_set_SessionTicket_cb(WOLFSSL* ssl,
3638
                                 CallbackSessionTicket cb, void* ctx)
3639
0
{
3640
0
    if (ssl == NULL)
3641
0
        return BAD_FUNC_ARG;
3642
3643
0
    ssl->session_ticket_cb = cb;
3644
0
    ssl->session_ticket_ctx = ctx;
3645
3646
0
    return WOLFSSL_SUCCESS;
3647
0
}
3648
#endif /* !NO_WOLFSSL_CLIENT */
3649
3650
#endif /* HAVE_SESSION_TICKET */
3651
3652
3653
#ifdef HAVE_EXTENDED_MASTER
3654
#ifndef NO_WOLFSSL_CLIENT
3655
3656
int wolfSSL_CTX_DisableExtendedMasterSecret(WOLFSSL_CTX* ctx)
3657
0
{
3658
0
    if (ctx == NULL)
3659
0
        return BAD_FUNC_ARG;
3660
3661
0
    ctx->haveEMS = 0;
3662
3663
0
    return WOLFSSL_SUCCESS;
3664
0
}
3665
3666
3667
int wolfSSL_DisableExtendedMasterSecret(WOLFSSL* ssl)
3668
0
{
3669
0
    if (ssl == NULL)
3670
0
        return BAD_FUNC_ARG;
3671
3672
0
    ssl->options.haveEMS = 0;
3673
3674
0
    return WOLFSSL_SUCCESS;
3675
0
}
3676
3677
#endif
3678
#endif
3679
3680
3681
#ifndef WOLFSSL_LEANPSK
3682
3683
int wolfSSL_send(WOLFSSL* ssl, const void* data, int sz, int flags)
3684
0
{
3685
0
    int ret;
3686
0
    int oldFlags;
3687
3688
0
    WOLFSSL_ENTER("wolfSSL_send");
3689
3690
0
    if (ssl == NULL || data == NULL || sz < 0)
3691
0
        return BAD_FUNC_ARG;
3692
3693
0
    oldFlags = ssl->wflags;
3694
3695
0
    ssl->wflags = flags;
3696
0
    ret = wolfSSL_write(ssl, data, sz);
3697
0
    ssl->wflags = oldFlags;
3698
3699
0
    WOLFSSL_LEAVE("wolfSSL_send", ret);
3700
3701
0
    return ret;
3702
0
}
3703
3704
3705
int wolfSSL_recv(WOLFSSL* ssl, void* data, int sz, int flags)
3706
0
{
3707
0
    int ret;
3708
0
    int oldFlags;
3709
3710
0
    WOLFSSL_ENTER("wolfSSL_recv");
3711
3712
0
    if (ssl == NULL || data == NULL || sz < 0)
3713
0
        return BAD_FUNC_ARG;
3714
3715
0
    oldFlags = ssl->rflags;
3716
3717
0
    ssl->rflags = flags;
3718
0
    ret = wolfSSL_read(ssl, data, sz);
3719
0
    ssl->rflags = oldFlags;
3720
3721
0
    WOLFSSL_LEAVE("wolfSSL_recv", ret);
3722
3723
0
    return ret;
3724
0
}
3725
#endif
3726
3727
int wolfSSL_SendUserCanceled(WOLFSSL* ssl)
3728
0
{
3729
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
3730
0
    WOLFSSL_ENTER("wolfSSL_recv");
3731
3732
0
    if (ssl != NULL) {
3733
0
        ssl->error = SendAlert(ssl, alert_warning, user_canceled);
3734
0
        if (ssl->error < 0) {
3735
0
            WOLFSSL_ERROR(ssl->error);
3736
0
        }
3737
0
        else {
3738
0
            ret = wolfSSL_shutdown(ssl);
3739
0
        }
3740
0
    }
3741
3742
0
    WOLFSSL_LEAVE("wolfSSL_SendUserCanceled", ret);
3743
3744
0
    return ret;
3745
0
}
3746
3747
/* WOLFSSL_SUCCESS on ok */
3748
WOLFSSL_ABI
3749
int wolfSSL_shutdown(WOLFSSL* ssl)
3750
0
{
3751
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR);
3752
0
    WOLFSSL_ENTER("wolfSSL_shutdown");
3753
3754
0
    if (ssl == NULL)
3755
0
        return WOLFSSL_FATAL_ERROR;
3756
3757
0
    if (ssl->options.quietShutdown) {
3758
0
        WOLFSSL_MSG("quiet shutdown, no close notify sent");
3759
0
        ret = WOLFSSL_SUCCESS;
3760
0
    }
3761
0
    else {
3762
3763
        /* Try to flush the buffer first, it might contain the alert */
3764
0
        if (ssl->error == WC_NO_ERR_TRACE(WANT_WRITE) &&
3765
0
            ssl->buffers.outputBuffer.length > 0) {
3766
0
            ret = SendBuffered(ssl);
3767
0
            if (ret != 0) {
3768
0
                ssl->error = ret;
3769
                /* for error tracing */
3770
0
                if (ret != WC_NO_ERR_TRACE(WANT_WRITE))
3771
0
                    WOLFSSL_ERROR(ret);
3772
0
                ret = WOLFSSL_FATAL_ERROR;
3773
0
                WOLFSSL_LEAVE("wolfSSL_shutdown", ret);
3774
0
                return ret;
3775
0
            }
3776
3777
0
            ssl->error = WOLFSSL_ERROR_NONE;
3778
            /* we succeeded in sending the alert now */
3779
0
            if (ssl->options.sentNotify)  {
3780
                /* just after we send the alert, if we didn't receive the alert
3781
                 * from the other peer yet, return WOLFSSL_STHUDOWN_NOT_DONE */
3782
0
                if (!ssl->options.closeNotify) {
3783
0
                    ret = WOLFSSL_SHUTDOWN_NOT_DONE;
3784
0
                    WOLFSSL_LEAVE("wolfSSL_shutdown", ret);
3785
0
                    return ret;
3786
0
                }
3787
0
                else {
3788
0
                    ssl->options.shutdownDone = 1;
3789
0
                    ret = WOLFSSL_SUCCESS;
3790
0
                }
3791
0
            }
3792
0
        }
3793
3794
        /* try to send close notify, not an error if can't */
3795
0
        if (!ssl->options.isClosed && !ssl->options.connReset &&
3796
0
                                      !ssl->options.sentNotify) {
3797
0
            ssl->error = SendAlert(ssl, alert_warning, close_notify);
3798
3799
            /* the alert is now sent or sitting in the buffer,
3800
             * where will be sent eventually */
3801
0
            if (ssl->error == 0 || ssl->error == WC_NO_ERR_TRACE(WANT_WRITE))
3802
0
                ssl->options.sentNotify = 1;
3803
3804
0
            if (ssl->error < 0) {
3805
0
                WOLFSSL_ERROR(ssl->error);
3806
0
                return WOLFSSL_FATAL_ERROR;
3807
0
            }
3808
3809
0
            if (ssl->options.closeNotify) {
3810
0
                ret = WOLFSSL_SUCCESS;
3811
0
                ssl->options.shutdownDone = 1;
3812
0
            }
3813
0
            else {
3814
0
                ret = WOLFSSL_SHUTDOWN_NOT_DONE;
3815
0
                WOLFSSL_LEAVE("wolfSSL_shutdown", ret);
3816
0
                return ret;
3817
0
            }
3818
0
        }
3819
3820
#ifdef WOLFSSL_SHUTDOWNONCE
3821
        if (ssl->options.isClosed || ssl->options.connReset) {
3822
            /* Shutdown has already occurred.
3823
             * Caller is free to ignore this error. */
3824
            return SSL_SHUTDOWN_ALREADY_DONE_E;
3825
        }
3826
#endif
3827
3828
        /* wolfSSL_shutdown called again for bidirectional shutdown */
3829
0
        if (ssl->options.sentNotify && !ssl->options.closeNotify) {
3830
0
            ret = ProcessReply(ssl);
3831
0
            if ((ret == WC_NO_ERR_TRACE(ZERO_RETURN)) ||
3832
0
                (ret == WC_NO_ERR_TRACE(SOCKET_ERROR_E))) {
3833
                /* simulate OpenSSL behavior */
3834
0
                ssl->options.shutdownDone = 1;
3835
                /* Clear error */
3836
0
                ssl->error = WOLFSSL_ERROR_NONE;
3837
0
                ret = WOLFSSL_SUCCESS;
3838
0
            }
3839
0
            else if (ret == WC_NO_ERR_TRACE(MEMORY_E)) {
3840
0
                ret = WOLFSSL_FATAL_ERROR;
3841
0
            }
3842
0
            else if (ret == WC_NO_ERR_TRACE(WANT_READ)) {
3843
0
                ssl->error = ret;
3844
0
                ret = WOLFSSL_FATAL_ERROR;
3845
0
            }
3846
0
            else if (ssl->error == WOLFSSL_ERROR_NONE) {
3847
0
                ret = WOLFSSL_SHUTDOWN_NOT_DONE;
3848
0
            }
3849
0
            else {
3850
0
                WOLFSSL_ERROR(ssl->error);
3851
0
                ret = WOLFSSL_FATAL_ERROR;
3852
0
            }
3853
0
        }
3854
0
    }
3855
3856
0
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
3857
    /* reset WOLFSSL structure state for possible reuse */
3858
0
    if (ret == WOLFSSL_SUCCESS) {
3859
0
        if (wolfSSL_clear(ssl) != WOLFSSL_SUCCESS) {
3860
0
            WOLFSSL_MSG("could not clear WOLFSSL");
3861
0
            ret = WOLFSSL_FATAL_ERROR;
3862
0
        }
3863
0
    }
3864
0
#endif
3865
3866
0
    WOLFSSL_LEAVE("wolfSSL_shutdown", ret);
3867
3868
0
    return ret;
3869
0
}
3870
#endif /* !NO_TLS */
3871
3872
/* get current error state value */
3873
int wolfSSL_state(WOLFSSL* ssl)
3874
0
{
3875
0
    if (ssl == NULL) {
3876
0
        return BAD_FUNC_ARG;
3877
0
    }
3878
3879
0
    return ssl->error;
3880
0
}
3881
3882
3883
WOLFSSL_ABI
3884
int wolfSSL_get_error(WOLFSSL* ssl, int ret)
3885
0
{
3886
0
    WOLFSSL_ENTER("wolfSSL_get_error");
3887
3888
0
    if (ret > 0)
3889
0
        return WOLFSSL_ERROR_NONE;
3890
0
    if (ssl == NULL)
3891
0
        return BAD_FUNC_ARG;
3892
3893
0
    WOLFSSL_LEAVE("wolfSSL_get_error", ssl->error);
3894
3895
    /* make sure converted types are handled in SetErrorString() too */
3896
0
    if (ssl->error == WC_NO_ERR_TRACE(WANT_READ))
3897
0
        return WOLFSSL_ERROR_WANT_READ;         /* convert to OpenSSL type */
3898
0
    else if (ssl->error == WC_NO_ERR_TRACE(WANT_WRITE))
3899
0
        return WOLFSSL_ERROR_WANT_WRITE;        /* convert to OpenSSL type */
3900
0
    else if (ssl->error == WC_NO_ERR_TRACE(ZERO_RETURN) ||
3901
0
             ssl->options.shutdownDone)
3902
0
        return WOLFSSL_ERROR_ZERO_RETURN;       /* convert to OpenSSL type */
3903
0
#ifdef OPENSSL_EXTRA
3904
0
    else if (ssl->error == WC_NO_ERR_TRACE(MATCH_SUITE_ERROR))
3905
0
        return WOLFSSL_ERROR_SYSCALL;           /* convert to OpenSSL type */
3906
0
    else if (ssl->error == WC_NO_ERR_TRACE(SOCKET_PEER_CLOSED_E))
3907
0
        return WOLFSSL_ERROR_SYSCALL;           /* convert to OpenSSL type */
3908
0
#endif
3909
#ifdef WOLFSSL_ASYNC_CRYPT
3910
    else if (ssl->error == WC_NO_ERR_TRACE(MP_WOULDBLOCK))
3911
        return WC_PENDING_E;                    /* map non-blocking crypto */
3912
#endif
3913
0
    return ssl->error;
3914
0
}
3915
3916
3917
/* retrieve alert history, WOLFSSL_SUCCESS on ok */
3918
int wolfSSL_get_alert_history(WOLFSSL* ssl, WOLFSSL_ALERT_HISTORY *h)
3919
0
{
3920
0
    if (ssl && h) {
3921
0
        *h = ssl->alert_history;
3922
0
    }
3923
0
    return WOLFSSL_SUCCESS;
3924
0
}
3925
3926
#ifdef OPENSSL_EXTRA
3927
/* returns SSL_WRITING, SSL_READING or SSL_NOTHING */
3928
int wolfSSL_want(WOLFSSL* ssl)
3929
0
{
3930
0
    int rw_state = WOLFSSL_NOTHING;
3931
0
    if (ssl) {
3932
0
        if (ssl->error == WC_NO_ERR_TRACE(WANT_READ))
3933
0
            rw_state = WOLFSSL_READING;
3934
0
        else if (ssl->error == WC_NO_ERR_TRACE(WANT_WRITE))
3935
0
            rw_state = WOLFSSL_WRITING;
3936
0
    }
3937
0
    return rw_state;
3938
0
}
3939
#endif
3940
3941
/* return TRUE if current error is want read */
3942
int wolfSSL_want_read(WOLFSSL* ssl)
3943
0
{
3944
0
    WOLFSSL_ENTER("wolfSSL_want_read");
3945
0
    if (ssl->error == WC_NO_ERR_TRACE(WANT_READ))
3946
0
        return 1;
3947
3948
0
    return 0;
3949
0
}
3950
3951
/* return TRUE if current error is want write */
3952
int wolfSSL_want_write(WOLFSSL* ssl)
3953
0
{
3954
0
    WOLFSSL_ENTER("wolfSSL_want_write");
3955
0
    if (ssl->error == WC_NO_ERR_TRACE(WANT_WRITE))
3956
0
        return 1;
3957
3958
0
    return 0;
3959
0
}
3960
3961
char* wolfSSL_ERR_error_string(unsigned long errNumber, char* data)
3962
0
{
3963
0
    WOLFSSL_ENTER("wolfSSL_ERR_error_string");
3964
0
    if (data) {
3965
0
        SetErrorString((int)errNumber, data);
3966
0
        return data;
3967
0
    }
3968
0
    else {
3969
0
        static char tmp[WOLFSSL_MAX_ERROR_SZ] = {0};
3970
0
        SetErrorString((int)errNumber, tmp);
3971
0
        return tmp;
3972
0
    }
3973
0
}
3974
3975
3976
void wolfSSL_ERR_error_string_n(unsigned long e, char* buf, unsigned long len)
3977
0
{
3978
0
    WOLFSSL_ENTER("wolfSSL_ERR_error_string_n");
3979
0
    if (len >= WOLFSSL_MAX_ERROR_SZ)
3980
0
        wolfSSL_ERR_error_string(e, buf);
3981
0
    else {
3982
0
        WOLFSSL_MSG("Error buffer too short, truncating");
3983
0
        if (len) {
3984
0
            char tmp[WOLFSSL_MAX_ERROR_SZ];
3985
0
            wolfSSL_ERR_error_string(e, tmp);
3986
0
            XMEMCPY(buf, tmp, len-1);
3987
0
            buf[len-1] = '\0';
3988
0
        }
3989
0
    }
3990
0
}
3991
3992
3993
/* don't free temporary arrays at end of handshake */
3994
void wolfSSL_KeepArrays(WOLFSSL* ssl)
3995
0
{
3996
0
    if (ssl)
3997
0
        ssl->options.saveArrays = 1;
3998
0
}
3999
4000
4001
/* user doesn't need temporary arrays anymore, Free */
4002
void wolfSSL_FreeArrays(WOLFSSL* ssl)
4003
0
{
4004
0
    if (ssl && ssl->options.handShakeState == HANDSHAKE_DONE) {
4005
0
        ssl->options.saveArrays = 0;
4006
0
        FreeArrays(ssl, 1);
4007
0
    }
4008
0
}
4009
4010
/* Set option to indicate that the resources are not to be freed after
4011
 * handshake.
4012
 *
4013
 * ssl  The SSL/TLS object.
4014
 * returns BAD_FUNC_ARG when ssl is NULL and 0 on success.
4015
 */
4016
int wolfSSL_KeepHandshakeResources(WOLFSSL* ssl)
4017
0
{
4018
0
    if (ssl == NULL)
4019
0
        return BAD_FUNC_ARG;
4020
4021
0
    ssl->options.keepResources = 1;
4022
4023
0
    return 0;
4024
0
}
4025
4026
/* Free the handshake resources after handshake.
4027
 *
4028
 * ssl  The SSL/TLS object.
4029
 * returns BAD_FUNC_ARG when ssl is NULL and 0 on success.
4030
 */
4031
int wolfSSL_FreeHandshakeResources(WOLFSSL* ssl)
4032
0
{
4033
0
    if (ssl == NULL)
4034
0
        return BAD_FUNC_ARG;
4035
4036
0
    FreeHandshakeResources(ssl);
4037
4038
0
    return 0;
4039
0
}
4040
4041
/* Use the client's order of preference when matching cipher suites.
4042
 *
4043
 * ssl  The SSL/TLS context object.
4044
 * returns BAD_FUNC_ARG when ssl is NULL and 0 on success.
4045
 */
4046
int wolfSSL_CTX_UseClientSuites(WOLFSSL_CTX* ctx)
4047
0
{
4048
0
    if (ctx == NULL)
4049
0
        return BAD_FUNC_ARG;
4050
4051
0
    ctx->useClientOrder = 1;
4052
4053
0
    return 0;
4054
0
}
4055
4056
/* Use the client's order of preference when matching cipher suites.
4057
 *
4058
 * ssl  The SSL/TLS object.
4059
 * returns BAD_FUNC_ARG when ssl is NULL and 0 on success.
4060
 */
4061
int wolfSSL_UseClientSuites(WOLFSSL* ssl)
4062
0
{
4063
0
    if (ssl == NULL)
4064
0
        return BAD_FUNC_ARG;
4065
4066
0
    ssl->options.useClientOrder = 1;
4067
4068
0
    return 0;
4069
0
}
4070
4071
#ifdef WOLFSSL_DTLS
4072
const byte* wolfSSL_GetDtlsMacSecret(WOLFSSL* ssl, int verify, int epochOrder)
4073
{
4074
#ifndef WOLFSSL_AEAD_ONLY
4075
    Keys* keys = NULL;
4076
4077
    (void)epochOrder;
4078
4079
    if (ssl == NULL)
4080
        return NULL;
4081
4082
#ifdef HAVE_SECURE_RENEGOTIATION
4083
    switch (epochOrder) {
4084
    case PEER_ORDER:
4085
        if (IsDtlsMsgSCRKeys(ssl))
4086
            keys = &ssl->secure_renegotiation->tmp_keys;
4087
        else
4088
            keys = &ssl->keys;
4089
        break;
4090
    case PREV_ORDER:
4091
        keys = &ssl->keys;
4092
        break;
4093
    case CUR_ORDER:
4094
        if (DtlsUseSCRKeys(ssl))
4095
            keys = &ssl->secure_renegotiation->tmp_keys;
4096
        else
4097
            keys = &ssl->keys;
4098
        break;
4099
    default:
4100
        WOLFSSL_MSG("Unknown epoch order");
4101
        return NULL;
4102
    }
4103
#else
4104
    keys = &ssl->keys;
4105
#endif
4106
4107
    if ( (ssl->options.side == WOLFSSL_CLIENT_END && !verify) ||
4108
         (ssl->options.side == WOLFSSL_SERVER_END &&  verify) )
4109
        return keys->client_write_MAC_secret;
4110
    else
4111
        return keys->server_write_MAC_secret;
4112
#else
4113
    (void)ssl;
4114
    (void)verify;
4115
    (void)epochOrder;
4116
4117
    return NULL;
4118
#endif
4119
}
4120
#endif /* WOLFSSL_DTLS */
4121
4122
const byte* wolfSSL_GetMacSecret(WOLFSSL* ssl, int verify)
4123
660
{
4124
660
#ifndef WOLFSSL_AEAD_ONLY
4125
660
    if (ssl == NULL)
4126
0
        return NULL;
4127
4128
660
    if ( (ssl->options.side == WOLFSSL_CLIENT_END && !verify) ||
4129
144
         (ssl->options.side == WOLFSSL_SERVER_END &&  verify) )
4130
563
        return ssl->keys.client_write_MAC_secret;
4131
97
    else
4132
97
        return ssl->keys.server_write_MAC_secret;
4133
#else
4134
    (void)ssl;
4135
    (void)verify;
4136
4137
    return NULL;
4138
#endif
4139
660
}
4140
4141
int wolfSSL_GetSide(WOLFSSL* ssl)
4142
0
{
4143
0
    if (ssl)
4144
0
        return ssl->options.side;
4145
4146
0
    return BAD_FUNC_ARG;
4147
0
}
4148
4149
#ifdef ATOMIC_USER
4150
4151
void  wolfSSL_CTX_SetMacEncryptCb(WOLFSSL_CTX* ctx, CallbackMacEncrypt cb)
4152
{
4153
    if (ctx)
4154
        ctx->MacEncryptCb = cb;
4155
}
4156
4157
4158
void  wolfSSL_SetMacEncryptCtx(WOLFSSL* ssl, void *ctx)
4159
{
4160
    if (ssl)
4161
        ssl->MacEncryptCtx = ctx;
4162
}
4163
4164
4165
void* wolfSSL_GetMacEncryptCtx(WOLFSSL* ssl)
4166
{
4167
    if (ssl)
4168
        return ssl->MacEncryptCtx;
4169
4170
    return NULL;
4171
}
4172
4173
4174
void  wolfSSL_CTX_SetDecryptVerifyCb(WOLFSSL_CTX* ctx, CallbackDecryptVerify cb)
4175
{
4176
    if (ctx)
4177
        ctx->DecryptVerifyCb = cb;
4178
}
4179
4180
4181
void  wolfSSL_SetDecryptVerifyCtx(WOLFSSL* ssl, void *ctx)
4182
{
4183
    if (ssl)
4184
        ssl->DecryptVerifyCtx = ctx;
4185
}
4186
4187
4188
void* wolfSSL_GetDecryptVerifyCtx(WOLFSSL* ssl)
4189
{
4190
    if (ssl)
4191
        return ssl->DecryptVerifyCtx;
4192
4193
    return NULL;
4194
}
4195
4196
#if defined(HAVE_ENCRYPT_THEN_MAC) && !defined(WOLFSSL_AEAD_ONLY)
4197
/**
4198
 * Set the callback, against the context, that encrypts then MACs.
4199
 *
4200
 * ctx  SSL/TLS context.
4201
 * cb   Callback function to use with Encrypt-Then-MAC.
4202
 */
4203
void  wolfSSL_CTX_SetEncryptMacCb(WOLFSSL_CTX* ctx, CallbackEncryptMac cb)
4204
{
4205
    if (ctx)
4206
        ctx->EncryptMacCb = cb;
4207
}
4208
4209
/**
4210
 * Set the context to use with callback that encrypts then MACs.
4211
 *
4212
 * ssl  SSL/TLS object.
4213
 * ctx  Callback function's context.
4214
 */
4215
void  wolfSSL_SetEncryptMacCtx(WOLFSSL* ssl, void *ctx)
4216
{
4217
    if (ssl)
4218
        ssl->EncryptMacCtx = ctx;
4219
}
4220
4221
/**
4222
 * Get the context being used with callback that encrypts then MACs.
4223
 *
4224
 * ssl  SSL/TLS object.
4225
 * returns callback function's context or NULL if SSL/TLS object is NULL.
4226
 */
4227
void* wolfSSL_GetEncryptMacCtx(WOLFSSL* ssl)
4228
{
4229
    if (ssl)
4230
        return ssl->EncryptMacCtx;
4231
4232
    return NULL;
4233
}
4234
4235
4236
/**
4237
 * Set the callback, against the context, that MAC verifies then decrypts.
4238
 *
4239
 * ctx  SSL/TLS context.
4240
 * cb   Callback function to use with Encrypt-Then-MAC.
4241
 */
4242
void  wolfSSL_CTX_SetVerifyDecryptCb(WOLFSSL_CTX* ctx, CallbackVerifyDecrypt cb)
4243
{
4244
    if (ctx)
4245
        ctx->VerifyDecryptCb = cb;
4246
}
4247
4248
/**
4249
 * Set the context to use with callback that MAC verifies then decrypts.
4250
 *
4251
 * ssl  SSL/TLS object.
4252
 * ctx  Callback function's context.
4253
 */
4254
void  wolfSSL_SetVerifyDecryptCtx(WOLFSSL* ssl, void *ctx)
4255
{
4256
    if (ssl)
4257
        ssl->VerifyDecryptCtx = ctx;
4258
}
4259
4260
/**
4261
 * Get the context being used with callback that MAC verifies then decrypts.
4262
 *
4263
 * ssl  SSL/TLS object.
4264
 * returns callback function's context or NULL if SSL/TLS object is NULL.
4265
 */
4266
void* wolfSSL_GetVerifyDecryptCtx(WOLFSSL* ssl)
4267
{
4268
    if (ssl)
4269
        return ssl->VerifyDecryptCtx;
4270
4271
    return NULL;
4272
}
4273
#endif /* HAVE_ENCRYPT_THEN_MAC !WOLFSSL_AEAD_ONLY */
4274
4275
4276
4277
const byte* wolfSSL_GetClientWriteKey(WOLFSSL* ssl)
4278
{
4279
    if (ssl)
4280
        return ssl->keys.client_write_key;
4281
4282
    return NULL;
4283
}
4284
4285
4286
const byte* wolfSSL_GetClientWriteIV(WOLFSSL* ssl)
4287
{
4288
    if (ssl)
4289
        return ssl->keys.client_write_IV;
4290
4291
    return NULL;
4292
}
4293
4294
4295
const byte* wolfSSL_GetServerWriteKey(WOLFSSL* ssl)
4296
{
4297
    if (ssl)
4298
        return ssl->keys.server_write_key;
4299
4300
    return NULL;
4301
}
4302
4303
4304
const byte* wolfSSL_GetServerWriteIV(WOLFSSL* ssl)
4305
{
4306
    if (ssl)
4307
        return ssl->keys.server_write_IV;
4308
4309
    return NULL;
4310
}
4311
4312
int wolfSSL_GetKeySize(WOLFSSL* ssl)
4313
{
4314
    if (ssl)
4315
        return ssl->specs.key_size;
4316
4317
    return BAD_FUNC_ARG;
4318
}
4319
4320
4321
int wolfSSL_GetIVSize(WOLFSSL* ssl)
4322
{
4323
    if (ssl)
4324
        return ssl->specs.iv_size;
4325
4326
    return BAD_FUNC_ARG;
4327
}
4328
4329
4330
int wolfSSL_GetBulkCipher(WOLFSSL* ssl)
4331
{
4332
    if (ssl)
4333
        return ssl->specs.bulk_cipher_algorithm;
4334
4335
    return BAD_FUNC_ARG;
4336
}
4337
4338
4339
int wolfSSL_GetCipherType(WOLFSSL* ssl)
4340
{
4341
    if (ssl == NULL)
4342
        return BAD_FUNC_ARG;
4343
4344
#ifndef WOLFSSL_AEAD_ONLY
4345
    if (ssl->specs.cipher_type == block)
4346
        return WOLFSSL_BLOCK_TYPE;
4347
    if (ssl->specs.cipher_type == stream)
4348
        return WOLFSSL_STREAM_TYPE;
4349
#endif
4350
    if (ssl->specs.cipher_type == aead)
4351
        return WOLFSSL_AEAD_TYPE;
4352
4353
    return WOLFSSL_FATAL_ERROR;
4354
}
4355
4356
4357
int wolfSSL_GetCipherBlockSize(WOLFSSL* ssl)
4358
{
4359
    if (ssl == NULL)
4360
        return BAD_FUNC_ARG;
4361
4362
    return ssl->specs.block_size;
4363
}
4364
4365
4366
int wolfSSL_GetAeadMacSize(WOLFSSL* ssl)
4367
{
4368
    if (ssl == NULL)
4369
        return BAD_FUNC_ARG;
4370
4371
    return ssl->specs.aead_mac_size;
4372
}
4373
4374
4375
int wolfSSL_IsTLSv1_1(WOLFSSL* ssl)
4376
{
4377
    if (ssl == NULL)
4378
        return BAD_FUNC_ARG;
4379
4380
    if (ssl->options.tls1_1)
4381
        return 1;
4382
4383
    return 0;
4384
}
4385
4386
4387
4388
int wolfSSL_GetHmacSize(WOLFSSL* ssl)
4389
{
4390
    /* AEAD ciphers don't have HMAC keys */
4391
    if (ssl)
4392
        return (ssl->specs.cipher_type != aead) ? ssl->specs.hash_size : 0;
4393
4394
    return BAD_FUNC_ARG;
4395
}
4396
4397
#ifdef WORD64_AVAILABLE
4398
int wolfSSL_GetPeerSequenceNumber(WOLFSSL* ssl, word64 *seq)
4399
{
4400
    if ((ssl == NULL) || (seq == NULL))
4401
        return BAD_FUNC_ARG;
4402
4403
    *seq = ((word64)ssl->keys.peer_sequence_number_hi << 32) |
4404
                    ssl->keys.peer_sequence_number_lo;
4405
    return !(*seq);
4406
}
4407
4408
int wolfSSL_GetSequenceNumber(WOLFSSL* ssl, word64 *seq)
4409
{
4410
    if ((ssl == NULL) || (seq == NULL))
4411
        return BAD_FUNC_ARG;
4412
4413
    *seq = ((word64)ssl->keys.sequence_number_hi << 32) |
4414
                    ssl->keys.sequence_number_lo;
4415
    return !(*seq);
4416
}
4417
#endif
4418
4419
#endif /* ATOMIC_USER */
4420
4421
#if !defined(NO_FILESYSTEM) && !defined(NO_STDIO_FILESYSTEM) \
4422
    && defined(XFPRINTF)
4423
4424
void wolfSSL_ERR_print_errors_fp(XFILE fp, int err)
4425
0
{
4426
0
    char data[WOLFSSL_MAX_ERROR_SZ + 1];
4427
4428
0
    WOLFSSL_ENTER("wolfSSL_ERR_print_errors_fp");
4429
0
    SetErrorString(err, data);
4430
0
    if (XFPRINTF(fp, "%s", data) < 0)
4431
0
        WOLFSSL_MSG("fprintf failed in wolfSSL_ERR_print_errors_fp");
4432
0
}
4433
4434
#if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE)
4435
void wolfSSL_ERR_dump_errors_fp(XFILE fp)
4436
0
{
4437
0
    wc_ERR_print_errors_fp(fp);
4438
0
}
4439
4440
void wolfSSL_ERR_print_errors_cb (int (*cb)(const char *str, size_t len,
4441
                                            void *u), void *u)
4442
0
{
4443
0
    wc_ERR_print_errors_cb(cb, u);
4444
0
}
4445
#endif
4446
#endif /* !NO_FILESYSTEM && !NO_STDIO_FILESYSTEM && XFPRINTF */
4447
4448
/*
4449
 * TODO This ssl parameter needs to be changed to const once our ABI checker
4450
 *      stops flagging qualifier additions as ABI breaking.
4451
 */
4452
WOLFSSL_ABI
4453
int wolfSSL_pending(WOLFSSL* ssl)
4454
0
{
4455
0
    WOLFSSL_ENTER("wolfSSL_pending");
4456
0
    if (ssl == NULL)
4457
0
        return WOLFSSL_FAILURE;
4458
4459
0
    return (int)ssl->buffers.clearOutputBuffer.length;
4460
0
}
4461
4462
int wolfSSL_has_pending(const WOLFSSL* ssl)
4463
0
{
4464
0
    WOLFSSL_ENTER("wolfSSL_has_pending");
4465
0
    if (ssl == NULL)
4466
0
        return WOLFSSL_FAILURE;
4467
4468
0
    return ssl->buffers.clearOutputBuffer.length > 0;
4469
0
}
4470
4471
#ifndef WOLFSSL_LEANPSK
4472
/* turn on handshake group messages for context */
4473
int wolfSSL_CTX_set_group_messages(WOLFSSL_CTX* ctx)
4474
0
{
4475
0
    if (ctx == NULL)
4476
0
       return BAD_FUNC_ARG;
4477
4478
0
    ctx->groupMessages = 1;
4479
4480
0
    return WOLFSSL_SUCCESS;
4481
0
}
4482
4483
int wolfSSL_CTX_clear_group_messages(WOLFSSL_CTX* ctx)
4484
0
{
4485
0
    if (ctx == NULL)
4486
0
       return BAD_FUNC_ARG;
4487
4488
0
    ctx->groupMessages = 0;
4489
4490
0
    return WOLFSSL_SUCCESS;
4491
0
}
4492
#endif
4493
4494
4495
#if !defined(NO_WOLFSSL_CLIENT) && !defined(NO_TLS)
4496
/* connect enough to get peer cert chain */
4497
int wolfSSL_connect_cert(WOLFSSL* ssl)
4498
0
{
4499
0
    int  ret;
4500
4501
0
    if (ssl == NULL)
4502
0
        return WOLFSSL_FAILURE;
4503
4504
0
    ssl->options.certOnly = 1;
4505
0
    ret = wolfSSL_connect(ssl);
4506
0
    ssl->options.certOnly   = 0;
4507
4508
0
    return ret;
4509
0
}
4510
#endif
4511
4512
4513
#ifndef WOLFSSL_LEANPSK
4514
/* turn on handshake group messages for ssl object */
4515
int wolfSSL_set_group_messages(WOLFSSL* ssl)
4516
0
{
4517
0
    if (ssl == NULL)
4518
0
       return BAD_FUNC_ARG;
4519
4520
0
    ssl->options.groupMessages = 1;
4521
4522
0
    return WOLFSSL_SUCCESS;
4523
0
}
4524
4525
int wolfSSL_clear_group_messages(WOLFSSL* ssl)
4526
0
{
4527
0
    if (ssl == NULL)
4528
0
       return BAD_FUNC_ARG;
4529
4530
0
    ssl->options.groupMessages = 0;
4531
4532
0
    return WOLFSSL_SUCCESS;
4533
0
}
4534
4535
/* make minVersion the internal equivalent SSL version */
4536
static int SetMinVersionHelper(byte* minVersion, int version)
4537
0
{
4538
0
    (void)minVersion;
4539
4540
0
    switch (version) {
4541
#if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS)
4542
        case WOLFSSL_SSLV3:
4543
            *minVersion = SSLv3_MINOR;
4544
            break;
4545
#endif
4546
4547
0
#ifndef NO_TLS
4548
    #ifndef NO_OLD_TLS
4549
        #ifdef WOLFSSL_ALLOW_TLSV10
4550
        case WOLFSSL_TLSV1:
4551
            *minVersion = TLSv1_MINOR;
4552
            break;
4553
        #endif
4554
4555
        case WOLFSSL_TLSV1_1:
4556
            *minVersion = TLSv1_1_MINOR;
4557
            break;
4558
    #endif
4559
0
    #ifndef WOLFSSL_NO_TLS12
4560
0
        case WOLFSSL_TLSV1_2:
4561
0
            *minVersion = TLSv1_2_MINOR;
4562
0
            break;
4563
0
    #endif
4564
0
#endif
4565
0
    #ifdef WOLFSSL_TLS13
4566
0
        case WOLFSSL_TLSV1_3:
4567
0
            *minVersion = TLSv1_3_MINOR;
4568
0
            break;
4569
0
    #endif
4570
4571
#ifdef WOLFSSL_DTLS
4572
        case WOLFSSL_DTLSV1:
4573
            *minVersion = DTLS_MINOR;
4574
            break;
4575
        case WOLFSSL_DTLSV1_2:
4576
            *minVersion = DTLSv1_2_MINOR;
4577
            break;
4578
#ifdef WOLFSSL_DTLS13
4579
        case WOLFSSL_DTLSV1_3:
4580
            *minVersion = DTLSv1_3_MINOR;
4581
            break;
4582
#endif /* WOLFSSL_DTLS13 */
4583
#endif /* WOLFSSL_DTLS */
4584
4585
0
        default:
4586
0
            WOLFSSL_MSG("Bad function argument");
4587
0
            return BAD_FUNC_ARG;
4588
0
    }
4589
4590
0
    return WOLFSSL_SUCCESS;
4591
0
}
4592
4593
4594
/* Set minimum downgrade version allowed, WOLFSSL_SUCCESS on ok */
4595
WOLFSSL_ABI
4596
int wolfSSL_CTX_SetMinVersion(WOLFSSL_CTX* ctx, int version)
4597
0
{
4598
0
    WOLFSSL_ENTER("wolfSSL_CTX_SetMinVersion");
4599
4600
0
    if (ctx == NULL) {
4601
0
        WOLFSSL_MSG("Bad function argument");
4602
0
        return BAD_FUNC_ARG;
4603
0
    }
4604
4605
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
4606
    if (crypto_policy.enabled) {
4607
        return CRYPTO_POLICY_FORBIDDEN;
4608
    }
4609
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
4610
4611
0
    return SetMinVersionHelper(&ctx->minDowngrade, version);
4612
0
}
4613
4614
4615
/* Set minimum downgrade version allowed, WOLFSSL_SUCCESS on ok */
4616
int wolfSSL_SetMinVersion(WOLFSSL* ssl, int version)
4617
0
{
4618
0
    WOLFSSL_ENTER("wolfSSL_SetMinVersion");
4619
4620
0
    if (ssl == NULL) {
4621
0
        WOLFSSL_MSG("Bad function argument");
4622
0
        return BAD_FUNC_ARG;
4623
0
    }
4624
4625
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
4626
    if (crypto_policy.enabled) {
4627
        return CRYPTO_POLICY_FORBIDDEN;
4628
    }
4629
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
4630
4631
0
    return SetMinVersionHelper(&ssl->options.minDowngrade, version);
4632
0
}
4633
4634
4635
/* Function to get version as WOLFSSL_ enum value for wolfSSL_SetVersion */
4636
int wolfSSL_GetVersion(const WOLFSSL* ssl)
4637
0
{
4638
0
    if (ssl == NULL)
4639
0
        return BAD_FUNC_ARG;
4640
4641
0
    if (ssl->version.major == SSLv3_MAJOR) {
4642
0
        switch (ssl->version.minor) {
4643
0
            case SSLv3_MINOR :
4644
0
                return WOLFSSL_SSLV3;
4645
0
            case TLSv1_MINOR :
4646
0
                return WOLFSSL_TLSV1;
4647
0
            case TLSv1_1_MINOR :
4648
0
                return WOLFSSL_TLSV1_1;
4649
0
            case TLSv1_2_MINOR :
4650
0
                return WOLFSSL_TLSV1_2;
4651
0
            case TLSv1_3_MINOR :
4652
0
                return WOLFSSL_TLSV1_3;
4653
0
            default:
4654
0
                break;
4655
0
        }
4656
0
    }
4657
#ifdef WOLFSSL_DTLS
4658
    if (ssl->version.major == DTLS_MAJOR) {
4659
        switch (ssl->version.minor) {
4660
            case DTLS_MINOR :
4661
                return WOLFSSL_DTLSV1;
4662
            case DTLSv1_2_MINOR :
4663
                return WOLFSSL_DTLSV1_2;
4664
            case DTLSv1_3_MINOR :
4665
                return WOLFSSL_DTLSV1_3;
4666
            default:
4667
                break;
4668
        }
4669
    }
4670
#endif /* WOLFSSL_DTLS */
4671
4672
0
    return VERSION_ERROR;
4673
0
}
4674
4675
int wolfSSL_SetVersion(WOLFSSL* ssl, int version)
4676
0
{
4677
0
    word16 haveRSA = 1;
4678
0
    word16 havePSK = 0;
4679
0
    int    keySz   = 0;
4680
4681
0
    WOLFSSL_ENTER("wolfSSL_SetVersion");
4682
4683
0
    if (ssl == NULL) {
4684
0
        WOLFSSL_MSG("Bad function argument");
4685
0
        return BAD_FUNC_ARG;
4686
0
    }
4687
4688
0
    switch (version) {
4689
#if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS)
4690
        case WOLFSSL_SSLV3:
4691
            ssl->version = MakeSSLv3();
4692
            break;
4693
#endif
4694
4695
0
#ifndef NO_TLS
4696
    #ifndef NO_OLD_TLS
4697
        #ifdef WOLFSSL_ALLOW_TLSV10
4698
        case WOLFSSL_TLSV1:
4699
            ssl->version = MakeTLSv1();
4700
            break;
4701
        #endif
4702
4703
        case WOLFSSL_TLSV1_1:
4704
            ssl->version = MakeTLSv1_1();
4705
            break;
4706
    #endif
4707
0
    #ifndef WOLFSSL_NO_TLS12
4708
0
        case WOLFSSL_TLSV1_2:
4709
0
            ssl->version = MakeTLSv1_2();
4710
0
            break;
4711
0
    #endif
4712
4713
0
    #ifdef WOLFSSL_TLS13
4714
0
        case WOLFSSL_TLSV1_3:
4715
0
            ssl->version = MakeTLSv1_3();
4716
0
            break;
4717
0
    #endif /* WOLFSSL_TLS13 */
4718
0
#endif
4719
4720
0
        default:
4721
0
            WOLFSSL_MSG("Bad function argument");
4722
0
            return BAD_FUNC_ARG;
4723
0
    }
4724
4725
0
    ssl->options.downgrade = 0;
4726
4727
    #ifdef NO_RSA
4728
        haveRSA = 0;
4729
    #endif
4730
    #ifndef NO_PSK
4731
        havePSK = ssl->options.havePSK;
4732
    #endif
4733
0
    #ifndef NO_CERTS
4734
0
        keySz = ssl->buffers.keySz;
4735
0
    #endif
4736
4737
0
    if (AllocateSuites(ssl) != 0)
4738
0
        return WOLFSSL_FAILURE;
4739
0
    InitSuites(ssl->suites, ssl->version, keySz, haveRSA, havePSK,
4740
0
               ssl->options.haveDH, ssl->options.haveECDSAsig,
4741
0
               ssl->options.haveECC, TRUE, ssl->options.haveStaticECC,
4742
0
               ssl->options.useAnon, TRUE, TRUE, TRUE, TRUE, ssl->options.side);
4743
0
    return WOLFSSL_SUCCESS;
4744
0
}
4745
#endif /* !leanpsk */
4746
4747
#if defined(OPENSSL_EXTRA) && !defined(WOLFSSL_NO_OPENSSL_RAND_CB)
4748
static int wolfSSL_RAND_InitMutex(void);
4749
#endif
4750
4751
/* If we don't have static mutex initializers, but we do have static atomic
4752
 * initializers, activate WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS to leverage
4753
 * the latter.
4754
 *
4755
 * See further explanation below in wolfSSL_Init().
4756
 */
4757
#ifndef WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
4758
    #if !defined(WOLFSSL_MUTEX_INITIALIZER) && !defined(SINGLE_THREADED) && \
4759
            defined(WOLFSSL_ATOMIC_OPS) && defined(WOLFSSL_ATOMIC_INITIALIZER)
4760
        #define WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS 1
4761
    #else
4762
        #define WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS 0
4763
    #endif
4764
#elif defined(WOLFSSL_MUTEX_INITIALIZER) || defined(SINGLE_THREADED)
4765
    #undef WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
4766
    #define WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS 0
4767
#endif
4768
4769
#if WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
4770
    #ifndef WOLFSSL_ATOMIC_OPS
4771
        #error WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS requires WOLFSSL_ATOMIC_OPS
4772
    #endif
4773
    #ifndef WOLFSSL_ATOMIC_INITIALIZER
4774
        #error WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS requires WOLFSSL_ATOMIC_INITIALIZER
4775
    #endif
4776
    static wolfSSL_Atomic_Int inits_count_mutex_atomic_initing_flag =
4777
        WOLFSSL_ATOMIC_INITIALIZER(0);
4778
#endif /* WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS && !WOLFSSL_MUTEX_INITIALIZER */
4779
4780
#if defined(OPENSSL_EXTRA) && defined(HAVE_ATEXIT)
4781
static void AtExitCleanup(void)
4782
16
{
4783
16
    if (initRefCount > 0) {
4784
14
        initRefCount = 1;
4785
14
        (void)wolfSSL_Cleanup();
4786
#if WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
4787
        if (inits_count_mutex_valid == 1) {
4788
            (void)wc_FreeMutex(&inits_count_mutex);
4789
            inits_count_mutex_valid = 0;
4790
            inits_count_mutex_atomic_initing_flag = 0;
4791
        }
4792
#endif
4793
14
    }
4794
16
}
4795
#endif
4796
4797
WOLFSSL_ABI
4798
int wolfSSL_Init(void)
4799
16
{
4800
16
    int ret = WOLFSSL_SUCCESS;
4801
#if !defined(NO_SESSION_CACHE) && defined(ENABLE_SESSION_CACHE_ROW_LOCK)
4802
    int i;
4803
#endif
4804
4805
16
    WOLFSSL_ENTER("wolfSSL_Init");
4806
4807
16
#if defined(LIBWOLFSSL_CMAKE_OUTPUT)
4808
16
    WOLFSSL_MSG(LIBWOLFSSL_CMAKE_OUTPUT);
4809
#else
4810
    WOLFSSL_MSG("No extra wolfSSL cmake messages found");
4811
#endif
4812
4813
#ifndef WOLFSSL_MUTEX_INITIALIZER
4814
    if (inits_count_mutex_valid == 0) {
4815
    #if WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
4816
4817
        /* Without this mitigation, if two threads enter wolfSSL_Init() at the
4818
         * same time, and both see zero inits_count_mutex_valid, then both will
4819
         * run wc_InitMutex(&inits_count_mutex), leading to process corruption
4820
         * or (best case) a resource leak.
4821
         *
4822
         * When WOLFSSL_ATOMIC_INITIALIZER() is available, we can mitigate this
4823
         * by use an atomic counting int as a mutex.
4824
         */
4825
4826
        if (wolfSSL_Atomic_Int_FetchAdd(&inits_count_mutex_atomic_initing_flag,
4827
                                        1) != 0)
4828
        {
4829
            (void)wolfSSL_Atomic_Int_FetchSub(
4830
                &inits_count_mutex_atomic_initing_flag, 1);
4831
            return DEADLOCK_AVERTED_E;
4832
        }
4833
    #endif /* WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS */
4834
        if (wc_InitMutex(&inits_count_mutex) != 0) {
4835
            WOLFSSL_MSG("Bad Init Mutex count");
4836
    #if WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
4837
            (void)wolfSSL_Atomic_Int_FetchSub(
4838
                &inits_count_mutex_atomic_initing_flag, 1);
4839
    #endif
4840
            return BAD_MUTEX_E;
4841
        }
4842
        else {
4843
            inits_count_mutex_valid = 1;
4844
        }
4845
    }
4846
#endif /* !WOLFSSL_MUTEX_INITIALIZER */
4847
4848
16
    if (wc_LockMutex(&inits_count_mutex) != 0) {
4849
0
        WOLFSSL_MSG("Bad Lock Mutex count");
4850
0
        return BAD_MUTEX_E;
4851
0
    }
4852
4853
#if FIPS_VERSION_GE(5,1)
4854
    if ((ret == WOLFSSL_SUCCESS) && (initRefCount == 0)) {
4855
        ret = wolfCrypt_SetPrivateKeyReadEnable_fips(1, WC_KEYTYPE_ALL);
4856
        if (ret == 0)
4857
            ret = WOLFSSL_SUCCESS;
4858
    }
4859
#endif
4860
4861
16
    if ((ret == WOLFSSL_SUCCESS) && (initRefCount == 0)) {
4862
        /* Initialize crypto for use with TLS connection */
4863
4864
16
        if (wolfCrypt_Init() != 0) {
4865
0
            WOLFSSL_MSG("Bad wolfCrypt Init");
4866
0
            ret = WC_INIT_E;
4867
0
        }
4868
4869
#if defined(HAVE_GLOBAL_RNG) && !defined(WOLFSSL_MUTEX_INITIALIZER)
4870
        if (ret == WOLFSSL_SUCCESS) {
4871
            if (wc_InitMutex(&globalRNGMutex) != 0) {
4872
                WOLFSSL_MSG("Bad Init Mutex rng");
4873
                ret = BAD_MUTEX_E;
4874
            }
4875
            else {
4876
                globalRNGMutex_valid = 1;
4877
            }
4878
        }
4879
#endif
4880
4881
    #ifdef WC_RNG_SEED_CB
4882
        wc_SetSeed_Cb(WC_GENERATE_SEED_DEFAULT);
4883
    #endif
4884
4885
16
#ifdef OPENSSL_EXTRA
4886
16
    #ifndef WOLFSSL_NO_OPENSSL_RAND_CB
4887
16
        if ((ret == WOLFSSL_SUCCESS) && (wolfSSL_RAND_InitMutex() != 0)) {
4888
0
            ret = BAD_MUTEX_E;
4889
0
        }
4890
16
    #endif
4891
16
        if ((ret == WOLFSSL_SUCCESS) &&
4892
16
            (wolfSSL_RAND_seed(NULL, 0) != WOLFSSL_SUCCESS)) {
4893
0
            WOLFSSL_MSG("wolfSSL_RAND_seed failed");
4894
0
            ret = WC_INIT_E;
4895
0
        }
4896
16
#endif
4897
4898
16
#ifndef NO_SESSION_CACHE
4899
    #ifdef ENABLE_SESSION_CACHE_ROW_LOCK
4900
        for (i = 0; i < SESSION_ROWS; ++i) {
4901
            SessionCache[i].lock_valid = 0;
4902
        }
4903
        for (i = 0; (ret == WOLFSSL_SUCCESS) && (i < SESSION_ROWS); ++i) {
4904
            if (wc_InitRwLock(&SessionCache[i].row_lock) != 0) {
4905
                WOLFSSL_MSG("Bad Init Mutex session");
4906
                ret = BAD_MUTEX_E;
4907
            }
4908
            else {
4909
                SessionCache[i].lock_valid = 1;
4910
            }
4911
        }
4912
    #else
4913
16
        if (ret == WOLFSSL_SUCCESS) {
4914
16
            if (wc_InitRwLock(&session_lock) != 0) {
4915
0
                WOLFSSL_MSG("Bad Init Mutex session");
4916
0
                ret = BAD_MUTEX_E;
4917
0
            }
4918
16
            else {
4919
16
                session_lock_valid = 1;
4920
16
            }
4921
16
        }
4922
16
    #endif
4923
16
    #ifndef NO_CLIENT_CACHE
4924
        #ifndef WOLFSSL_MUTEX_INITIALIZER
4925
        if (ret == WOLFSSL_SUCCESS) {
4926
            if (wc_InitMutex(&clisession_mutex) != 0) {
4927
                WOLFSSL_MSG("Bad Init Mutex session");
4928
                ret = BAD_MUTEX_E;
4929
            }
4930
            else {
4931
                clisession_mutex_valid = 1;
4932
            }
4933
        }
4934
        #endif
4935
16
    #endif
4936
16
#endif
4937
16
#if defined(OPENSSL_EXTRA) && defined(HAVE_ATEXIT)
4938
        /* OpenSSL registers cleanup using atexit */
4939
16
        if ((ret == WOLFSSL_SUCCESS) && (atexit(AtExitCleanup) != 0)) {
4940
0
            WOLFSSL_MSG("Bad atexit registration");
4941
0
            ret = WC_INIT_E;
4942
0
        }
4943
16
#endif
4944
16
    }
4945
4946
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
4947
    /* System wide crypto policy disabled by default. */
4948
    XMEMSET(&crypto_policy, 0, sizeof(crypto_policy));
4949
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
4950
4951
16
    if (ret == WOLFSSL_SUCCESS) {
4952
16
        initRefCount = initRefCount + 1;
4953
16
    }
4954
0
    else {
4955
0
        initRefCount = 1; /* Force cleanup */
4956
0
    }
4957
4958
16
    wc_UnLockMutex(&inits_count_mutex);
4959
4960
16
    if (ret != WOLFSSL_SUCCESS) {
4961
0
        (void)wolfSSL_Cleanup(); /* Ignore any error from cleanup */
4962
0
    }
4963
4964
16
    return ret;
4965
16
}
4966
4967
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
4968
/* Helper function for wolfSSL_crypto_policy_enable and
4969
 * wolfSSL_crypto_policy_enable_buffer.
4970
 *
4971
 * Parses the crypto policy string, verifies values,
4972
 * and sets in global crypto policy struct. Not thread
4973
 * safe. String length has already been verified.
4974
 *
4975
 * Returns WOLFSSL_SUCCESS on success.
4976
 * Returns CRYPTO_POLICY_FORBIDDEN if already enabled.
4977
 * Returns < 0 on misc error.
4978
 * */
4979
static int crypto_policy_parse(void)
4980
{
4981
    const char * hdr = WOLFSSL_SECLEVEL_STR;
4982
    int          sec_level = 0;
4983
    size_t       i = 0;
4984
4985
    /* All policies should begin with "@SECLEVEL=<N>" (N={0..5}) followed
4986
     * by bulk cipher list. */
4987
    if (XMEMCMP(crypto_policy.str, hdr, strlen(hdr)) != 0) {
4988
        WOLFSSL_MSG("error: crypto policy: invalid header");
4989
        return WOLFSSL_BAD_FILE;
4990
    }
4991
4992
    {
4993
        /* Extract the security level. */
4994
        char *       policy_mem = crypto_policy.str;
4995
        policy_mem += strlen(hdr);
4996
        sec_level = (int) (*policy_mem - '0');
4997
    }
4998
4999
    if (sec_level < MIN_WOLFSSL_SEC_LEVEL ||
5000
        sec_level > MAX_WOLFSSL_SEC_LEVEL) {
5001
        WOLFSSL_MSG_EX("error: invalid SECLEVEL: %d", sec_level);
5002
        return WOLFSSL_BAD_FILE;
5003
    }
5004
5005
    /* Remove trailing '\r' or '\n'. */
5006
    for (i = 0; i < MAX_WOLFSSL_CRYPTO_POLICY_SIZE; ++i) {
5007
        if (crypto_policy.str[i] == '\0') {
5008
            break;
5009
        }
5010
5011
        if (crypto_policy.str[i] == '\r' || crypto_policy.str[i] == '\n') {
5012
            crypto_policy.str[i] = '\0';
5013
            break;
5014
        }
5015
    }
5016
5017
    #if defined(DEBUG_WOLFSSL_VERBOSE)
5018
    WOLFSSL_MSG_EX("info: SECLEVEL=%d", sec_level);
5019
    WOLFSSL_MSG_EX("info: using crypto-policy file: %s, %ld", policy_file, sz);
5020
    #endif /* DEBUG_WOLFSSL_VERBOSE */
5021
5022
    crypto_policy.secLevel = sec_level;
5023
    crypto_policy.enabled = 1;
5024
5025
    return WOLFSSL_SUCCESS;
5026
}
5027
5028
#ifndef NO_FILESYSTEM
5029
/* Enables wolfSSL system wide crypto-policy, using the given policy
5030
 * file arg. If NULL is passed, then the default system crypto-policy
5031
 * file that was set at configure time will be used instead.
5032
 *
5033
 * While enabled:
5034
 *   - TLS methods, min key sizes, and cipher lists are all configured
5035
 *     automatically by the policy.
5036
 *   - Attempting to use lesser strength parameters will fail with
5037
 *     error CRYPTO_POLICY_FORBIDDEN.
5038
 *
5039
 * Disable with wolfSSL_crypto_policy_disable.
5040
 *
5041
 * Note: the wolfSSL_crypto_policy_X API are not thread safe, and should
5042
 * only be called at program init time.
5043
 *
5044
 * Returns WOLFSSL_SUCCESS on success.
5045
 * Returns CRYPTO_POLICY_FORBIDDEN if already enabled.
5046
 * Returns < 0 on misc error.
5047
 * */
5048
int wolfSSL_crypto_policy_enable(const char * policy_file)
5049
{
5050
    XFILE   file;
5051
    long    sz = 0;
5052
    size_t  n_read = 0;
5053
5054
    WOLFSSL_ENTER("wolfSSL_crypto_policy_enable");
5055
5056
    if (wolfSSL_crypto_policy_is_enabled()) {
5057
        WOLFSSL_MSG_EX("error: crypto policy already enabled: %s",
5058
                       policy_file);
5059
        return CRYPTO_POLICY_FORBIDDEN;
5060
    }
5061
5062
    if (policy_file == NULL) {
5063
        /* Use the configure-time default if NULL passed. */
5064
        policy_file = WC_STRINGIFY(WOLFSSL_CRYPTO_POLICY_FILE);
5065
    }
5066
5067
    if (policy_file == NULL || *policy_file == '\0') {
5068
        WOLFSSL_MSG("error: crypto policy empty file");
5069
        return BAD_FUNC_ARG;
5070
    }
5071
5072
    XMEMSET(&crypto_policy, 0, sizeof(crypto_policy));
5073
5074
    file = XFOPEN(policy_file, "rb");
5075
5076
    if (file == XBADFILE) {
5077
        WOLFSSL_MSG_EX("error: crypto policy file open failed: %s",
5078
                       policy_file);
5079
        return WOLFSSL_BAD_FILE;
5080
    }
5081
5082
    if (XFSEEK(file, 0, XSEEK_END) != 0) {
5083
        WOLFSSL_MSG_EX("error: crypto policy file seek end failed: %s",
5084
                       policy_file);
5085
        XFCLOSE(file);
5086
        return WOLFSSL_BAD_FILE;
5087
    }
5088
5089
    sz = XFTELL(file);
5090
5091
    if (XFSEEK(file, 0, XSEEK_SET) != 0) {
5092
        WOLFSSL_MSG_EX("error: crypto policy file seek failed: %s",
5093
                       policy_file);
5094
        XFCLOSE(file);
5095
        return WOLFSSL_BAD_FILE;
5096
    }
5097
5098
    if (sz <= 0 || sz > MAX_WOLFSSL_CRYPTO_POLICY_SIZE) {
5099
        WOLFSSL_MSG_EX("error: crypto policy file %s, invalid size: %ld",
5100
                       policy_file, sz);
5101
        XFCLOSE(file);
5102
        return WOLFSSL_BAD_FILE;
5103
    }
5104
5105
    n_read = XFREAD(crypto_policy.str, 1, sz, file);
5106
    XFCLOSE(file);
5107
5108
    if (n_read != (size_t) sz) {
5109
        WOLFSSL_MSG_EX("error: crypto policy file %s: read %zu, "
5110
                       "expected %ld", policy_file, n_read, sz);
5111
        return WOLFSSL_BAD_FILE;
5112
    }
5113
5114
    crypto_policy.str[n_read] = '\0';
5115
5116
    return crypto_policy_parse();
5117
}
5118
#endif /* ! NO_FILESYSTEM */
5119
5120
/* Same behavior as wolfSSL_crypto_policy_enable, but loads
5121
 * via memory buf instead of file.
5122
 *
5123
 * Returns WOLFSSL_SUCCESS on success.
5124
 * Returns CRYPTO_POLICY_FORBIDDEN if already enabled.
5125
 * Returns < 0 on misc error.
5126
 * */
5127
int wolfSSL_crypto_policy_enable_buffer(const char * buf)
5128
{
5129
    size_t sz = 0;
5130
5131
    WOLFSSL_ENTER("wolfSSL_crypto_policy_enable_buffer");
5132
5133
    if (wolfSSL_crypto_policy_is_enabled()) {
5134
        WOLFSSL_MSG_EX("error: crypto policy already enabled");
5135
        return CRYPTO_POLICY_FORBIDDEN;
5136
    }
5137
5138
    if (buf == NULL || *buf == '\0') {
5139
        return BAD_FUNC_ARG;
5140
    }
5141
5142
    sz = XSTRLEN(buf);
5143
5144
    if (sz == 0 || sz > MAX_WOLFSSL_CRYPTO_POLICY_SIZE) {
5145
        return BAD_FUNC_ARG;
5146
    }
5147
5148
    XMEMSET(&crypto_policy, 0, sizeof(crypto_policy));
5149
    XMEMCPY(crypto_policy.str, buf, sz);
5150
5151
    return crypto_policy_parse();
5152
}
5153
5154
/* Returns whether the system wide crypto-policy is enabled.
5155
 *
5156
 * Returns 1 if enabled.
5157
 *         0 if disabled.
5158
 * */
5159
int wolfSSL_crypto_policy_is_enabled(void)
5160
{
5161
    WOLFSSL_ENTER("wolfSSL_crypto_policy_is_enabled");
5162
5163
    return crypto_policy.enabled == 1;
5164
}
5165
5166
/* Disables the system wide crypto-policy.
5167
 * note: SSL and CTX structures already instantiated will
5168
 * keep their security policy parameters. This will only
5169
 * affect new instantiations.
5170
 * */
5171
void wolfSSL_crypto_policy_disable(void)
5172
{
5173
    WOLFSSL_ENTER("wolfSSL_crypto_policy_disable");
5174
    crypto_policy.enabled = 0;
5175
    XMEMSET(&crypto_policy, 0, sizeof(crypto_policy));
5176
    return;
5177
}
5178
5179
/* Get the crypto-policy bulk cipher list string.
5180
 * String is not owned by caller, should not be freed.
5181
 *
5182
 * Returns pointer to bulk cipher list string.
5183
 * Returns NULL if NOT enabled, or on error.
5184
 * */
5185
const char * wolfSSL_crypto_policy_get_ciphers(void)
5186
{
5187
    WOLFSSL_ENTER("wolfSSL_crypto_policy_get_ciphers");
5188
5189
    if (crypto_policy.enabled == 1) {
5190
        /* The crypto policy config will have
5191
         * this form:
5192
         *   "@SECLEVEL=2:kEECDH:kRSA..." */
5193
        return crypto_policy.str;
5194
    }
5195
5196
    return NULL;
5197
}
5198
5199
/* Get the configured crypto-policy security level.
5200
 * A security level of 0 does not impose any additional
5201
 * restrictions.
5202
 *
5203
 * Returns 1 - 5 if enabled.
5204
 * Returns 0 if NOT enabled.
5205
 * */
5206
int wolfSSL_crypto_policy_get_level(void)
5207
{
5208
    if (crypto_policy.enabled == 1) {
5209
        return crypto_policy.secLevel;
5210
    }
5211
5212
    return 0;
5213
}
5214
5215
/* Get security level from ssl structure.
5216
 * @param ssl  a pointer to WOLFSSL structure
5217
 */
5218
int wolfSSL_get_security_level(const WOLFSSL * ssl)
5219
{
5220
    if (ssl == NULL) {
5221
        return BAD_FUNC_ARG;
5222
    }
5223
5224
    return ssl->secLevel;
5225
}
5226
5227
#ifndef NO_WOLFSSL_STUB
5228
/*
5229
 * Set security level (wolfSSL doesn't support setting the security level).
5230
 *
5231
 * The security level can only be set through a system wide crypto-policy
5232
 * with wolfSSL_crypto_policy_enable().
5233
 *
5234
 * @param ssl  a pointer to WOLFSSL structure
5235
 * @param level security level
5236
 */
5237
void wolfSSL_set_security_level(WOLFSSL * ssl, int level)
5238
{
5239
    WOLFSSL_ENTER("wolfSSL_set_security_level");
5240
    (void)ssl;
5241
    (void)level;
5242
}
5243
#endif /* !NO_WOLFSSL_STUB */
5244
5245
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
5246
5247
5248
#define WOLFSSL_SSL_LOAD_INCLUDED
5249
#include <src/ssl_load.c>
5250
5251
#define WOLFSSL_SSL_API_CRL_OCSP_INCLUDED
5252
#include "src/ssl_api_crl_ocsp.c"
5253
5254
5255
void wolfSSL_load_error_strings(void)
5256
0
{
5257
    /* compatibility only */
5258
0
}
5259
5260
5261
int wolfSSL_library_init(void)
5262
0
{
5263
0
    WOLFSSL_ENTER("wolfSSL_library_init");
5264
0
    if (wolfSSL_Init() == WOLFSSL_SUCCESS)
5265
0
        return WOLFSSL_SUCCESS;
5266
0
    else
5267
0
        return WOLFSSL_FATAL_ERROR;
5268
0
}
5269
5270
5271
#ifdef HAVE_SECRET_CALLBACK
5272
5273
int wolfSSL_set_session_secret_cb(WOLFSSL* ssl, SessionSecretCb cb, void* ctx)
5274
{
5275
    WOLFSSL_ENTER("wolfSSL_set_session_secret_cb");
5276
    if (ssl == NULL)
5277
        return WOLFSSL_FAILURE;
5278
5279
    ssl->sessionSecretCb = cb;
5280
    ssl->sessionSecretCtx = ctx;
5281
    if (cb != NULL) {
5282
        /* If using a pre-set key, assume session resumption. */
5283
        ssl->session->sessionIDSz = 0;
5284
        ssl->options.resuming = 1;
5285
    }
5286
5287
    return WOLFSSL_SUCCESS;
5288
}
5289
5290
int wolfSSL_set_session_ticket_ext_cb(WOLFSSL* ssl, TicketParseCb cb,
5291
        void *ctx)
5292
{
5293
    WOLFSSL_ENTER("wolfSSL_set_session_ticket_ext_cb");
5294
    if (ssl == NULL)
5295
        return WOLFSSL_FAILURE;
5296
5297
    ssl->ticketParseCb = cb;
5298
    ssl->ticketParseCtx = ctx;
5299
5300
    return WOLFSSL_SUCCESS;
5301
}
5302
5303
int wolfSSL_set_secret_cb(WOLFSSL* ssl, TlsSecretCb cb, void* ctx)
5304
{
5305
    WOLFSSL_ENTER("wolfSSL_set_secret_cb");
5306
    if (ssl == NULL)
5307
        return WOLFSSL_FATAL_ERROR;
5308
5309
    ssl->tlsSecretCb = cb;
5310
    ssl->tlsSecretCtx = ctx;
5311
5312
    return WOLFSSL_SUCCESS;
5313
}
5314
5315
#ifdef SHOW_SECRETS
5316
int tlsShowSecrets(WOLFSSL* ssl, void* secret, int secretSz,
5317
        void* ctx)
5318
{
5319
    /* Wireshark Pre-Master-Secret Format:
5320
     *  CLIENT_RANDOM <clientrandom> <mastersecret>
5321
     */
5322
    const char* CLIENT_RANDOM_LABEL = "CLIENT_RANDOM";
5323
    int i, pmsPos = 0;
5324
    char pmsBuf[13 + 1 + 64 + 1 + 96 + 1 + 1];
5325
    byte clientRandom[RAN_LEN];
5326
    int clientRandomSz;
5327
5328
    (void)ctx;
5329
5330
    clientRandomSz = (int)wolfSSL_get_client_random(ssl, clientRandom,
5331
        sizeof(clientRandom));
5332
5333
    if (clientRandomSz <= 0) {
5334
        printf("Error getting server random %d\n", clientRandomSz);
5335
        return BAD_FUNC_ARG;
5336
    }
5337
5338
    XSNPRINTF(&pmsBuf[pmsPos], sizeof(pmsBuf) - pmsPos, "%s ",
5339
        CLIENT_RANDOM_LABEL);
5340
    pmsPos += XSTRLEN(CLIENT_RANDOM_LABEL) + 1;
5341
    for (i = 0; i < clientRandomSz; i++) {
5342
        XSNPRINTF(&pmsBuf[pmsPos], sizeof(pmsBuf) - pmsPos, "%02x",
5343
            clientRandom[i]);
5344
        pmsPos += 2;
5345
    }
5346
    XSNPRINTF(&pmsBuf[pmsPos], sizeof(pmsBuf) - pmsPos, " ");
5347
    pmsPos += 1;
5348
    for (i = 0; i < secretSz; i++) {
5349
        XSNPRINTF(&pmsBuf[pmsPos], sizeof(pmsBuf) - pmsPos, "%02x",
5350
            ((byte*)secret)[i]);
5351
        pmsPos += 2;
5352
    }
5353
    XSNPRINTF(&pmsBuf[pmsPos], sizeof(pmsBuf) - pmsPos, "\n");
5354
    pmsPos += 1;
5355
5356
    /* print master secret */
5357
    puts(pmsBuf);
5358
5359
    #if !defined(NO_FILESYSTEM) && defined(WOLFSSL_SSLKEYLOGFILE)
5360
    {
5361
        FILE* f = XFOPEN(WOLFSSL_SSLKEYLOGFILE_OUTPUT, "a");
5362
        if (f != XBADFILE) {
5363
            XFWRITE(pmsBuf, 1, pmsPos, f);
5364
            XFCLOSE(f);
5365
        }
5366
    }
5367
    #endif
5368
    return 0;
5369
}
5370
#endif /* SHOW_SECRETS */
5371
5372
#endif
5373
5374
5375
#ifdef OPENSSL_EXTRA
5376
5377
/*
5378
 * check if the list has TLS13 and pre-TLS13 suites
5379
 * @param list cipher suite list that user want to set
5380
 *         (caller required to check for NULL)
5381
 * @return mixed: 0, only pre-TLS13: 1, only TLS13: 2
5382
 */
5383
static int CheckcipherList(const char* list)
5384
48
{
5385
48
    int ret;
5386
48
    int findTLSv13Suites = 0;
5387
48
    int findbeforeSuites = 0;
5388
48
    byte cipherSuite0;
5389
48
    byte cipherSuite1;
5390
48
    int flags;
5391
48
    char* next = (char*)list;
5392
5393
768
    do {
5394
768
        char*  current = next;
5395
768
        char   name[MAX_SUITE_NAME + 1];
5396
768
        word32 length = MAX_SUITE_NAME;
5397
768
        word32 current_length;
5398
768
        byte major = INVALID_BYTE;
5399
768
        byte minor = INVALID_BYTE;
5400
5401
768
        next   = XSTRSTR(next, ":");
5402
5403
768
        if (next) {
5404
768
            current_length = (word32)(next - current);
5405
768
            ++next; /* increment to skip ':' */
5406
768
        }
5407
0
        else {
5408
0
            current_length = (word32)XSTRLEN(current);
5409
0
        }
5410
5411
768
        if (current_length == 0) {
5412
0
            break;
5413
0
        }
5414
5415
768
        if (current_length < length) {
5416
768
            length = current_length;
5417
768
        }
5418
768
        XMEMCPY(name, current, length);
5419
768
        name[length] = 0;
5420
5421
768
        if (XSTRCMP(name, "ALL") == 0 ||
5422
768
            XSTRCMP(name, "DEFAULT") == 0 ||
5423
768
            XSTRCMP(name, "HIGH") == 0)
5424
0
        {
5425
0
            findTLSv13Suites = 1;
5426
0
            findbeforeSuites = 1;
5427
0
            break;
5428
0
        }
5429
5430
768
        ret = GetCipherSuiteFromName(name, &cipherSuite0,
5431
768
                &cipherSuite1, &major, &minor, &flags);
5432
768
        if (ret == 0) {
5433
384
            if (cipherSuite0 == TLS13_BYTE || minor == TLSv1_3_MINOR) {
5434
                /* TLSv13 suite */
5435
336
                findTLSv13Suites = 1;
5436
336
            }
5437
48
            else {
5438
48
                findbeforeSuites = 1;
5439
48
            }
5440
384
        }
5441
5442
768
    #if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL)
5443
        /* check if mixed due to names like RSA:ECDHE+AESGCM etc. */
5444
768
        if (ret != 0) {
5445
384
            char* subStr = name;
5446
384
            char* subStrNext;
5447
5448
384
            do {
5449
384
                subStrNext = XSTRSTR(subStr, "+");
5450
5451
384
                if ((XSTRCMP(subStr, "ECDHE") == 0) ||
5452
384
                    (XSTRCMP(subStr, "RSA") == 0)) {
5453
0
                    return 0;
5454
0
                }
5455
5456
384
                if (subStrNext && (XSTRLEN(subStrNext) > 0)) {
5457
0
                    subStr = subStrNext + 1; /* +1 to skip past '+' */
5458
0
                }
5459
384
            } while (subStrNext != NULL);
5460
384
        }
5461
768
    #endif
5462
5463
768
        if (findTLSv13Suites == 1 && findbeforeSuites == 1) {
5464
            /* list has mixed suites */
5465
48
            return 0;
5466
48
        }
5467
768
    } while (next);
5468
5469
0
    if (findTLSv13Suites == 0 && findbeforeSuites == 1) {
5470
0
        ret = 1;/* only before TLSv13 suites */
5471
0
    }
5472
0
    else if (findTLSv13Suites == 1 && findbeforeSuites == 0) {
5473
0
        ret = 2;/* only TLSv13 suties */
5474
0
    }
5475
0
    else {
5476
0
        ret = 0;/* handle as mixed */
5477
0
    }
5478
0
    return ret;
5479
48
}
5480
5481
/* parse some bulk lists like !eNULL / !aNULL
5482
 *
5483
 * returns WOLFSSL_SUCCESS on success and sets the cipher suite list
5484
 */
5485
static int wolfSSL_parse_cipher_list(WOLFSSL_CTX* ctx, WOLFSSL* ssl,
5486
        Suites* suites, const char* list)
5487
48
{
5488
48
    int     ret = 0;
5489
48
    int     listattribute = 0;
5490
48
    int     tls13Only = 0;
5491
48
    WC_DECLARE_VAR(suitesCpy, byte, WOLFSSL_MAX_SUITE_SZ, 0);
5492
48
    word16  suitesCpySz = 0;
5493
48
    word16  i = 0;
5494
48
    word16  j = 0;
5495
5496
48
    if (suites == NULL || list == NULL) {
5497
0
        WOLFSSL_MSG("NULL argument");
5498
0
        return WOLFSSL_FAILURE;
5499
0
    }
5500
5501
48
    listattribute = CheckcipherList(list);
5502
5503
48
    if (listattribute == 0) {
5504
       /* list has mixed(pre-TLSv13 and TLSv13) suites
5505
        * update cipher suites the same as before
5506
        */
5507
48
        return (SetCipherList_ex(ctx, ssl, suites, list)) ? WOLFSSL_SUCCESS :
5508
48
        WOLFSSL_FAILURE;
5509
48
    }
5510
0
    else if (listattribute == 1) {
5511
       /* list has only pre-TLSv13 suites.
5512
        * Only update before TLSv13 suites.
5513
        */
5514
0
        tls13Only = 0;
5515
0
    }
5516
0
    else if (listattribute == 2) {
5517
       /* list has only TLSv13 suites. Only update TLv13 suites
5518
        * simulate set_ciphersuites() compatibility layer API
5519
        */
5520
0
        tls13Only = 1;
5521
0
        if ((ctx != NULL && !IsAtLeastTLSv1_3(ctx->method->version)) ||
5522
0
                (ssl != NULL && !IsAtLeastTLSv1_3(ssl->version))) {
5523
            /* Silently ignore TLS 1.3 ciphers if we don't support it. */
5524
0
            return WOLFSSL_SUCCESS;
5525
0
        }
5526
0
    }
5527
5528
    /* list contains ciphers either only for TLS 1.3 or <= TLS 1.2 */
5529
0
#ifdef WOLFSSL_SMALL_STACK
5530
0
    if (suites->suiteSz > 0) {
5531
0
        suitesCpy = (byte*)XMALLOC(suites->suiteSz, NULL,
5532
0
                DYNAMIC_TYPE_TMP_BUFFER);
5533
0
        if (suitesCpy == NULL) {
5534
0
            return WOLFSSL_FAILURE;
5535
0
        }
5536
5537
0
        XMEMSET(suitesCpy, 0, suites->suiteSz);
5538
0
    }
5539
#else
5540
        XMEMSET(suitesCpy, 0, sizeof(suitesCpy));
5541
#endif
5542
5543
0
    if (suites->suiteSz > 0)
5544
0
        XMEMCPY(suitesCpy, suites->suites, suites->suiteSz);
5545
0
    suitesCpySz = suites->suiteSz;
5546
5547
0
    ret = SetCipherList_ex(ctx, ssl, suites, list);
5548
0
    if (ret != 1) {
5549
0
        WC_FREE_VAR_EX(suitesCpy, NULL, DYNAMIC_TYPE_TMP_BUFFER);
5550
0
        return WOLFSSL_FAILURE;
5551
0
    }
5552
5553
    /* The idea in this section is that OpenSSL has two API to set ciphersuites.
5554
     *   - SSL_CTX_set_cipher_list for setting TLS <= 1.2 suites
5555
     *   - SSL_CTX_set_ciphersuites for setting TLS 1.3 suites
5556
     * Since we direct both API here we attempt to provide API compatibility. If
5557
     * we only get suites from <= 1.2 or == 1.3 then we will only update those
5558
     * suites and keep the suites from the other group.
5559
     * If downgrade is disabled, skip preserving the other group's suites. */
5560
0
    if ((ssl != NULL && !ssl->options.downgrade) ||
5561
0
        (ctx != NULL && !ctx->method->downgrade)) {
5562
        /* Downgrade disabled - don't preserve other group's suites */
5563
0
        WC_FREE_VAR_EX(suitesCpy, NULL, DYNAMIC_TYPE_TMP_BUFFER);
5564
0
        return ret;
5565
0
    }
5566
5567
0
    for (i = 0; i < suitesCpySz &&
5568
0
                suites->suiteSz <= (WOLFSSL_MAX_SUITE_SZ - SUITE_LEN); i += 2) {
5569
        /* Check for duplicates */
5570
0
        int duplicate = 0;
5571
0
        for (j = 0; j < suites->suiteSz; j += 2) {
5572
0
            if (suitesCpy[i] == suites->suites[j] &&
5573
0
                    suitesCpy[i+1] == suites->suites[j+1]) {
5574
0
                duplicate = 1;
5575
0
                break;
5576
0
            }
5577
0
        }
5578
0
        if (!duplicate) {
5579
0
            if (tls13Only) {
5580
                /* Updating TLS 1.3 ciphers */
5581
0
                if (suitesCpy[i] != TLS13_BYTE) {
5582
                    /* Only copy over <= TLS 1.2 ciphers */
5583
                    /* TLS 1.3 ciphers take precedence */
5584
0
                    suites->suites[suites->suiteSz++] = suitesCpy[i];
5585
0
                    suites->suites[suites->suiteSz++] = suitesCpy[i+1];
5586
0
                }
5587
0
            }
5588
0
            else {
5589
                /* Updating <= TLS 1.2 ciphers */
5590
0
                if (suitesCpy[i] == TLS13_BYTE) {
5591
                    /* Only copy over TLS 1.3 ciphers */
5592
                    /* TLS 1.3 ciphers take precedence */
5593
0
                    XMEMMOVE(suites->suites + SUITE_LEN, suites->suites,
5594
0
                             suites->suiteSz);
5595
0
                    suites->suites[0] = suitesCpy[i];
5596
0
                    suites->suites[1] = suitesCpy[i+1];
5597
0
                    suites->suiteSz += 2;
5598
0
                }
5599
0
            }
5600
0
        }
5601
0
    }
5602
5603
0
    WC_FREE_VAR_EX(suitesCpy, NULL, DYNAMIC_TYPE_TMP_BUFFER);
5604
0
    return ret;
5605
0
}
5606
5607
#endif
5608
5609
5610
int wolfSSL_CTX_set_cipher_list(WOLFSSL_CTX* ctx, const char* list)
5611
48
{
5612
48
    WOLFSSL_ENTER("wolfSSL_CTX_set_cipher_list");
5613
5614
48
    if (ctx == NULL)
5615
0
        return WOLFSSL_FAILURE;
5616
5617
48
    if (AllocateCtxSuites(ctx) != 0)
5618
0
        return WOLFSSL_FAILURE;
5619
5620
48
#ifdef OPENSSL_EXTRA
5621
48
    return wolfSSL_parse_cipher_list(ctx, NULL, ctx->suites, list);
5622
#else
5623
    return (SetCipherList(ctx, ctx->suites, list)) ?
5624
        WOLFSSL_SUCCESS : WOLFSSL_FAILURE;
5625
#endif
5626
48
}
5627
5628
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_SET_CIPHER_BYTES)
5629
int wolfSSL_CTX_set_cipher_list_bytes(WOLFSSL_CTX* ctx, const byte* list,
5630
                                      const int listSz)
5631
0
{
5632
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_cipher_list_bytes");
5633
5634
0
    if (ctx == NULL)
5635
0
        return WOLFSSL_FAILURE;
5636
5637
0
    if (AllocateCtxSuites(ctx) != 0)
5638
0
        return WOLFSSL_FAILURE;
5639
5640
0
    return (SetCipherListFromBytes(ctx, ctx->suites, list, listSz)) ?
5641
0
        WOLFSSL_SUCCESS : WOLFSSL_FAILURE;
5642
0
}
5643
#endif /* OPENSSL_EXTRA || WOLFSSL_SET_CIPHER_BYTES */
5644
5645
int wolfSSL_set_cipher_list(WOLFSSL* ssl, const char* list)
5646
0
{
5647
0
    WOLFSSL_ENTER("wolfSSL_set_cipher_list");
5648
5649
0
    if (ssl == NULL || ssl->ctx == NULL) {
5650
0
        return WOLFSSL_FAILURE;
5651
0
    }
5652
5653
0
    if (AllocateSuites(ssl) != 0)
5654
0
        return WOLFSSL_FAILURE;
5655
5656
0
#ifdef OPENSSL_EXTRA
5657
0
    return wolfSSL_parse_cipher_list(NULL, ssl, ssl->suites, list);
5658
#else
5659
    return (SetCipherList_ex(NULL, ssl, ssl->suites, list)) ?
5660
        WOLFSSL_SUCCESS :
5661
        WOLFSSL_FAILURE;
5662
#endif
5663
0
}
5664
5665
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_SET_CIPHER_BYTES)
5666
int wolfSSL_set_cipher_list_bytes(WOLFSSL* ssl, const byte* list,
5667
                                  const int listSz)
5668
0
{
5669
0
    WOLFSSL_ENTER("wolfSSL_set_cipher_list_bytes");
5670
5671
0
    if (ssl == NULL || ssl->ctx == NULL) {
5672
0
        return WOLFSSL_FAILURE;
5673
0
    }
5674
5675
0
    if (AllocateSuites(ssl) != 0)
5676
0
        return WOLFSSL_FAILURE;
5677
5678
0
    return (SetCipherListFromBytes(ssl->ctx, ssl->suites, list, listSz))
5679
0
           ? WOLFSSL_SUCCESS
5680
0
           : WOLFSSL_FAILURE;
5681
0
}
5682
#endif /* OPENSSL_EXTRA || WOLFSSL_SET_CIPHER_BYTES */
5683
5684
5685
#ifdef HAVE_KEYING_MATERIAL
5686
5687
#define TLS_PRF_LABEL_CLIENT_FINISHED     "client finished"
5688
#define TLS_PRF_LABEL_SERVER_FINISHED     "server finished"
5689
#define TLS_PRF_LABEL_MASTER_SECRET       "master secret"
5690
#define TLS_PRF_LABEL_EXT_MASTER_SECRET   "extended master secret"
5691
#define TLS_PRF_LABEL_KEY_EXPANSION       "key expansion"
5692
5693
static const struct ForbiddenLabels {
5694
    const char* label;
5695
    size_t labelLen;
5696
} forbiddenLabels[] = {
5697
    {TLS_PRF_LABEL_CLIENT_FINISHED, XSTR_SIZEOF(TLS_PRF_LABEL_CLIENT_FINISHED)},
5698
    {TLS_PRF_LABEL_SERVER_FINISHED, XSTR_SIZEOF(TLS_PRF_LABEL_SERVER_FINISHED)},
5699
    {TLS_PRF_LABEL_MASTER_SECRET, XSTR_SIZEOF(TLS_PRF_LABEL_MASTER_SECRET)},
5700
    {TLS_PRF_LABEL_EXT_MASTER_SECRET,
5701
     XSTR_SIZEOF(TLS_PRF_LABEL_EXT_MASTER_SECRET)},
5702
    {TLS_PRF_LABEL_KEY_EXPANSION, XSTR_SIZEOF(TLS_PRF_LABEL_KEY_EXPANSION)},
5703
    {NULL, 0},
5704
};
5705
5706
/**
5707
 * Implement RFC 5705
5708
 * TLS 1.3 uses a different exporter definition (section 7.5 of RFC 8446)
5709
 * @return WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE on error
5710
 */
5711
int wolfSSL_export_keying_material(WOLFSSL *ssl,
5712
        unsigned char *out, size_t outLen,
5713
        const char *label, size_t labelLen,
5714
        const unsigned char *context, size_t contextLen,
5715
        int use_context)
5716
{
5717
    byte*  seed = NULL;
5718
    word32 seedLen;
5719
    const struct ForbiddenLabels* fl;
5720
5721
    WOLFSSL_ENTER("wolfSSL_export_keying_material");
5722
5723
    if (ssl == NULL || out == NULL || label == NULL ||
5724
            (use_context && contextLen && context == NULL)) {
5725
        WOLFSSL_MSG("Bad argument");
5726
        return WOLFSSL_FAILURE;
5727
    }
5728
5729
    /* clientRandom + serverRandom
5730
     * OR
5731
     * clientRandom + serverRandom + ctx len encoding + ctx */
5732
    seedLen = !use_context ? (word32)SEED_LEN :
5733
                             (word32)SEED_LEN + 2 + (word32)contextLen;
5734
5735
    if (ssl->options.saveArrays == 0 || ssl->arrays == NULL) {
5736
        WOLFSSL_MSG("To export keying material wolfSSL needs to keep handshake "
5737
                    "data. Call wolfSSL_KeepArrays before attempting to "
5738
                    "export keyid material.");
5739
        return WOLFSSL_FAILURE;
5740
    }
5741
5742
    /* check forbidden labels */
5743
    for (fl = &forbiddenLabels[0]; fl->label != NULL; fl++) {
5744
        if (labelLen >= fl->labelLen &&
5745
                XMEMCMP(label, fl->label, fl->labelLen) == 0) {
5746
            WOLFSSL_MSG("Forbidden label");
5747
            return WOLFSSL_FAILURE;
5748
        }
5749
    }
5750
5751
#ifdef WOLFSSL_TLS13
5752
    if (IsAtLeastTLSv1_3(ssl->version)) {
5753
        /* Path for TLS 1.3 */
5754
        if (!use_context) {
5755
            contextLen = 0;
5756
            context = (byte*)""; /* Give valid pointer for 0 length memcpy */
5757
        }
5758
5759
        if (Tls13_Exporter(ssl, out, (word32)outLen, label, labelLen,
5760
                context, contextLen) != 0) {
5761
            WOLFSSL_MSG("Tls13_Exporter error");
5762
            return WOLFSSL_FAILURE;
5763
        }
5764
        return WOLFSSL_SUCCESS;
5765
    }
5766
#endif
5767
5768
    /* Path for <=TLS 1.2 */
5769
    seed = (byte*)XMALLOC(seedLen, NULL, DYNAMIC_TYPE_TMP_BUFFER);
5770
    if (seed == NULL) {
5771
        WOLFSSL_MSG("malloc error");
5772
        return WOLFSSL_FAILURE;
5773
    }
5774
5775
    XMEMCPY(seed,           ssl->arrays->clientRandom, RAN_LEN);
5776
    XMEMCPY(seed + RAN_LEN, ssl->arrays->serverRandom, RAN_LEN);
5777
5778
    if (use_context) {
5779
        /* Encode len in big endian */
5780
        seed[SEED_LEN    ] = (contextLen >> 8) & 0xFF;
5781
        seed[SEED_LEN + 1] = (contextLen) & 0xFF;
5782
        if (contextLen) {
5783
            /* 0 length context is allowed */
5784
            XMEMCPY(seed + SEED_LEN + 2, context, contextLen);
5785
        }
5786
    }
5787
5788
    PRIVATE_KEY_UNLOCK();
5789
    if (wc_PRF_TLS(out, (word32)outLen, ssl->arrays->masterSecret, SECRET_LEN,
5790
            (byte*)label, (word32)labelLen, seed, seedLen,
5791
            IsAtLeastTLSv1_2(ssl), ssl->specs.mac_algorithm, ssl->heap,
5792
            ssl->devId) != 0) {
5793
        WOLFSSL_MSG("wc_PRF_TLS error");
5794
        PRIVATE_KEY_LOCK();
5795
        XFREE(seed, NULL, DYNAMIC_TYPE_TMP_BUFFER);
5796
        return WOLFSSL_FAILURE;
5797
    }
5798
    PRIVATE_KEY_LOCK();
5799
5800
    XFREE(seed, NULL, DYNAMIC_TYPE_TMP_BUFFER);
5801
    return WOLFSSL_SUCCESS;
5802
}
5803
#endif /* HAVE_KEYING_MATERIAL */
5804
5805
int wolfSSL_dtls_get_using_nonblock(WOLFSSL* ssl)
5806
0
{
5807
0
    int useNb = 0;
5808
5809
0
    if (ssl == NULL)
5810
0
        return WOLFSSL_FAILURE;
5811
5812
0
    WOLFSSL_ENTER("wolfSSL_dtls_get_using_nonblock");
5813
0
    if (ssl->options.dtls) {
5814
#ifdef WOLFSSL_DTLS
5815
        useNb = ssl->options.dtlsUseNonblock;
5816
#endif
5817
0
    }
5818
0
    else {
5819
0
        WOLFSSL_MSG("wolfSSL_dtls_get_using_nonblock() is "
5820
0
                    "DEPRECATED for non-DTLS use.");
5821
0
    }
5822
0
    return useNb;
5823
0
}
5824
5825
5826
#ifndef WOLFSSL_LEANPSK
5827
5828
void wolfSSL_dtls_set_using_nonblock(WOLFSSL* ssl, int nonblock)
5829
0
{
5830
0
    (void)nonblock;
5831
5832
0
    WOLFSSL_ENTER("wolfSSL_dtls_set_using_nonblock");
5833
5834
0
    if (ssl == NULL)
5835
0
        return;
5836
5837
0
    if (ssl->options.dtls) {
5838
#ifdef WOLFSSL_DTLS
5839
        ssl->options.dtlsUseNonblock = (nonblock != 0);
5840
#endif
5841
0
    }
5842
0
    else {
5843
0
        WOLFSSL_MSG("wolfSSL_dtls_set_using_nonblock() is "
5844
0
                    "DEPRECATED for non-DTLS use.");
5845
0
    }
5846
0
}
5847
5848
5849
#ifdef WOLFSSL_DTLS
5850
5851
int wolfSSL_dtls_get_current_timeout(WOLFSSL* ssl)
5852
{
5853
    int timeout = 0;
5854
    if (ssl)
5855
        timeout = ssl->dtls_timeout;
5856
5857
    WOLFSSL_LEAVE("wolfSSL_dtls_get_current_timeout", timeout);
5858
    return timeout;
5859
}
5860
5861
#ifdef WOLFSSL_DTLS13
5862
5863
/*
5864
 * This API returns 1 when the user should set a short timeout for receiving
5865
 * data. It is recommended that it is at most 1/4 the value returned by
5866
 * wolfSSL_dtls_get_current_timeout().
5867
 */
5868
int wolfSSL_dtls13_use_quick_timeout(WOLFSSL* ssl)
5869
{
5870
    return ssl != NULL && ssl->dtls13FastTimeout;
5871
}
5872
5873
/*
5874
 * When this is set, a DTLS 1.3 connection will send acks immediately when a
5875
 * disruption is detected to shortcut timeouts. This results in potentially
5876
 * more traffic but may make the handshake quicker.
5877
 */
5878
void wolfSSL_dtls13_set_send_more_acks(WOLFSSL* ssl, int value)
5879
{
5880
    if (ssl != NULL)
5881
        ssl->options.dtls13SendMoreAcks = !!value;
5882
}
5883
#endif /* WOLFSSL_DTLS13 */
5884
5885
int wolfSSL_DTLSv1_get_timeout(WOLFSSL* ssl, WOLFSSL_TIMEVAL* timeleft)
5886
{
5887
    if (ssl && timeleft) {
5888
        XMEMSET(timeleft, 0, sizeof(WOLFSSL_TIMEVAL));
5889
        timeleft->tv_sec = ssl->dtls_timeout;
5890
    }
5891
    return 0;
5892
}
5893
5894
#ifndef NO_WOLFSSL_STUB
5895
int wolfSSL_DTLSv1_handle_timeout(WOLFSSL* ssl)
5896
{
5897
    WOLFSSL_STUB("SSL_DTLSv1_handle_timeout");
5898
    (void)ssl;
5899
    return 0;
5900
}
5901
#endif
5902
5903
#ifndef NO_WOLFSSL_STUB
5904
void wolfSSL_DTLSv1_set_initial_timeout_duration(WOLFSSL* ssl,
5905
    word32 duration_ms)
5906
{
5907
    WOLFSSL_STUB("SSL_DTLSv1_set_initial_timeout_duration");
5908
    (void)ssl;
5909
    (void)duration_ms;
5910
}
5911
#endif
5912
5913
/* user may need to alter init dtls recv timeout, WOLFSSL_SUCCESS on ok */
5914
int wolfSSL_dtls_set_timeout_init(WOLFSSL* ssl, int timeout)
5915
{
5916
    if (ssl == NULL || timeout < 0)
5917
        return BAD_FUNC_ARG;
5918
5919
    if (timeout > ssl->dtls_timeout_max) {
5920
        WOLFSSL_MSG("Can't set dtls timeout init greater than dtls timeout "
5921
                    "max");
5922
        return BAD_FUNC_ARG;
5923
    }
5924
5925
    ssl->dtls_timeout_init = timeout;
5926
    ssl->dtls_timeout = timeout;
5927
5928
    return WOLFSSL_SUCCESS;
5929
}
5930
5931
5932
/* user may need to alter max dtls recv timeout, WOLFSSL_SUCCESS on ok */
5933
int wolfSSL_dtls_set_timeout_max(WOLFSSL* ssl, int timeout)
5934
{
5935
    if (ssl == NULL || timeout < 0)
5936
        return BAD_FUNC_ARG;
5937
5938
    if (timeout < ssl->dtls_timeout_init) {
5939
        WOLFSSL_MSG("Can't set dtls timeout max less than dtls timeout init");
5940
        return BAD_FUNC_ARG;
5941
    }
5942
5943
    ssl->dtls_timeout_max = timeout;
5944
5945
    return WOLFSSL_SUCCESS;
5946
}
5947
5948
5949
int wolfSSL_dtls_got_timeout(WOLFSSL* ssl)
5950
{
5951
    int result = WOLFSSL_SUCCESS;
5952
    WOLFSSL_ENTER("wolfSSL_dtls_got_timeout");
5953
5954
    if (ssl == NULL || !ssl->options.dtls)
5955
        return WOLFSSL_FATAL_ERROR;
5956
5957
#ifdef WOLFSSL_DTLS13
5958
    if (IsAtLeastTLSv1_3(ssl->version)) {
5959
        result = Dtls13RtxTimeout(ssl);
5960
        if (result < 0) {
5961
            if (result == WC_NO_ERR_TRACE(WANT_WRITE))
5962
                ssl->dtls13SendingAckOrRtx = 1;
5963
            ssl->error = result;
5964
            WOLFSSL_ERROR(result);
5965
            return WOLFSSL_FATAL_ERROR;
5966
        }
5967
5968
        return WOLFSSL_SUCCESS;
5969
    }
5970
#endif /* WOLFSSL_DTLS13 */
5971
5972
    /* Do we have any 1.2 messages stored? */
5973
    if (ssl->dtls_tx_msg_list != NULL || ssl->dtls_tx_msg != NULL) {
5974
        if (DtlsMsgPoolTimeout(ssl) < 0){
5975
            ssl->error = SOCKET_ERROR_E;
5976
            WOLFSSL_ERROR(ssl->error);
5977
            result = WOLFSSL_FATAL_ERROR;
5978
        }
5979
        else if ((result = DtlsMsgPoolSend(ssl, 0)) < 0)  {
5980
            ssl->error = result;
5981
            WOLFSSL_ERROR(result);
5982
            result = WOLFSSL_FATAL_ERROR;
5983
        }
5984
        else {
5985
            /* Reset return value to success */
5986
            result = WOLFSSL_SUCCESS;
5987
        }
5988
    }
5989
5990
    WOLFSSL_LEAVE("wolfSSL_dtls_got_timeout", result);
5991
    return result;
5992
}
5993
5994
5995
/* retransmit all the saves messages, WOLFSSL_SUCCESS on ok */
5996
int wolfSSL_dtls_retransmit(WOLFSSL* ssl)
5997
{
5998
    WOLFSSL_ENTER("wolfSSL_dtls_retransmit");
5999
6000
    if (ssl == NULL)
6001
        return WOLFSSL_FATAL_ERROR;
6002
6003
    if (!ssl->options.handShakeDone) {
6004
        int result;
6005
#ifdef WOLFSSL_DTLS13
6006
        if (IsAtLeastTLSv1_3(ssl->version))
6007
            result = Dtls13DoScheduledWork(ssl);
6008
        else
6009
#endif
6010
            result = DtlsMsgPoolSend(ssl, 0);
6011
        if (result < 0) {
6012
            ssl->error = result;
6013
            WOLFSSL_ERROR(result);
6014
            return WOLFSSL_FATAL_ERROR;
6015
        }
6016
    }
6017
6018
    return WOLFSSL_SUCCESS;
6019
}
6020
6021
#endif /* DTLS */
6022
#endif /* LEANPSK */
6023
6024
6025
#if defined(WOLFSSL_DTLS) && !defined(NO_WOLFSSL_SERVER)
6026
6027
/* Not an SSL function, return 0 for success, error code otherwise */
6028
/* Prereq: ssl's RNG needs to be initialized. */
6029
int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
6030
                                 const byte* secret, word32 secretSz)
6031
{
6032
    int ret = 0;
6033
6034
    WOLFSSL_ENTER("wolfSSL_DTLS_SetCookieSecret");
6035
6036
    if (ssl == NULL) {
6037
        WOLFSSL_MSG("need a SSL object");
6038
        return BAD_FUNC_ARG;
6039
    }
6040
6041
    if (secret != NULL && secretSz == 0) {
6042
        WOLFSSL_MSG("can't have a new secret without a size");
6043
        return BAD_FUNC_ARG;
6044
    }
6045
6046
    /* If secretSz is 0, use the default size. */
6047
    if (secretSz == 0)
6048
        secretSz = COOKIE_SECRET_SZ;
6049
6050
    if (secretSz != ssl->buffers.dtlsCookieSecret.length) {
6051
        byte* newSecret;
6052
6053
        if (ssl->buffers.dtlsCookieSecret.buffer != NULL) {
6054
            ForceZero(ssl->buffers.dtlsCookieSecret.buffer,
6055
                      ssl->buffers.dtlsCookieSecret.length);
6056
            XFREE(ssl->buffers.dtlsCookieSecret.buffer,
6057
                  ssl->heap, DYNAMIC_TYPE_COOKIE_PWD);
6058
        }
6059
6060
        newSecret = (byte*)XMALLOC(secretSz, ssl->heap,DYNAMIC_TYPE_COOKIE_PWD);
6061
        if (newSecret == NULL) {
6062
            ssl->buffers.dtlsCookieSecret.buffer = NULL;
6063
            ssl->buffers.dtlsCookieSecret.length = 0;
6064
            WOLFSSL_MSG("couldn't allocate new cookie secret");
6065
            return MEMORY_ERROR;
6066
        }
6067
        ssl->buffers.dtlsCookieSecret.buffer = newSecret;
6068
        ssl->buffers.dtlsCookieSecret.length = secretSz;
6069
    #ifdef WOLFSSL_CHECK_MEM_ZERO
6070
        wc_MemZero_Add("wolfSSL_DTLS_SetCookieSecret secret",
6071
            ssl->buffers.dtlsCookieSecret.buffer,
6072
            ssl->buffers.dtlsCookieSecret.length);
6073
    #endif
6074
    }
6075
6076
    /* If the supplied secret is NULL, randomly generate a new secret. */
6077
    if (secret == NULL) {
6078
        ret = wc_RNG_GenerateBlock(ssl->rng,
6079
                             ssl->buffers.dtlsCookieSecret.buffer, secretSz);
6080
    }
6081
    else
6082
        XMEMCPY(ssl->buffers.dtlsCookieSecret.buffer, secret, secretSz);
6083
6084
    WOLFSSL_LEAVE("wolfSSL_DTLS_SetCookieSecret", 0);
6085
    return ret;
6086
}
6087
6088
#endif /* WOLFSSL_DTLS && !NO_WOLFSSL_SERVER */
6089
6090
6091
/* EITHER SIDE METHODS */
6092
#if !defined(NO_TLS) && (defined(OPENSSL_EXTRA) || defined(WOLFSSL_EITHER_SIDE))
6093
    WOLFSSL_METHOD* wolfSSLv23_method(void)
6094
0
    {
6095
0
        return wolfSSLv23_method_ex(NULL);
6096
0
    }
6097
    WOLFSSL_METHOD* wolfSSLv23_method_ex(void* heap)
6098
0
    {
6099
0
        WOLFSSL_METHOD* m = NULL;
6100
0
        WOLFSSL_ENTER("wolfSSLv23_method");
6101
0
    #if !defined(NO_WOLFSSL_CLIENT)
6102
0
        m = wolfSSLv23_client_method_ex(heap);
6103
    #elif !defined(NO_WOLFSSL_SERVER)
6104
        m = wolfSSLv23_server_method_ex(heap);
6105
    #else
6106
        (void)heap;
6107
    #endif
6108
0
        if (m != NULL) {
6109
0
            m->side = WOLFSSL_NEITHER_END;
6110
0
        }
6111
6112
0
        return m;
6113
0
    }
6114
6115
    #ifndef NO_OLD_TLS
6116
    #ifdef WOLFSSL_ALLOW_SSLV3
6117
    WOLFSSL_METHOD* wolfSSLv3_method(void)
6118
    {
6119
        return wolfSSLv3_method_ex(NULL);
6120
    }
6121
    WOLFSSL_METHOD* wolfSSLv3_method_ex(void* heap)
6122
    {
6123
        WOLFSSL_METHOD* m = NULL;
6124
        WOLFSSL_ENTER("wolfSSLv3_method_ex");
6125
    #if !defined(NO_WOLFSSL_CLIENT)
6126
        m = wolfSSLv3_client_method_ex(heap);
6127
    #elif !defined(NO_WOLFSSL_SERVER)
6128
        m = wolfSSLv3_server_method_ex(heap);
6129
    #endif
6130
        if (m != NULL) {
6131
            m->side = WOLFSSL_NEITHER_END;
6132
        }
6133
6134
        return m;
6135
    }
6136
    #endif
6137
    #endif
6138
#endif /* !NO_TLS && (OPENSSL_EXTRA || WOLFSSL_EITHER_SIDE) */
6139
6140
/* client only parts */
6141
#if !defined(NO_WOLFSSL_CLIENT) && !defined(NO_TLS)
6142
6143
    #if defined(OPENSSL_EXTRA) && !defined(NO_OLD_TLS)
6144
    WOLFSSL_METHOD* wolfSSLv2_client_method(void)
6145
    {
6146
        WOLFSSL_STUB("wolfSSLv2_client_method");
6147
        return NULL;
6148
    }
6149
    #endif
6150
6151
    #if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS)
6152
    WOLFSSL_METHOD* wolfSSLv3_client_method(void)
6153
    {
6154
        return wolfSSLv3_client_method_ex(NULL);
6155
    }
6156
    WOLFSSL_METHOD* wolfSSLv3_client_method_ex(void* heap)
6157
    {
6158
        WOLFSSL_METHOD* method =
6159
                              (WOLFSSL_METHOD*) XMALLOC(sizeof(WOLFSSL_METHOD),
6160
                                                     heap, DYNAMIC_TYPE_METHOD);
6161
        (void)heap;
6162
        WOLFSSL_ENTER("wolfSSLv3_client_method_ex");
6163
        if (method)
6164
            InitSSL_Method(method, MakeSSLv3());
6165
        return method;
6166
    }
6167
    #endif /* WOLFSSL_ALLOW_SSLV3 && !NO_OLD_TLS */
6168
6169
6170
    WOLFSSL_METHOD* wolfSSLv23_client_method(void)
6171
0
    {
6172
0
        return wolfSSLv23_client_method_ex(NULL);
6173
0
    }
6174
    WOLFSSL_METHOD* wolfSSLv23_client_method_ex(void* heap)
6175
0
    {
6176
0
        WOLFSSL_METHOD* method =
6177
0
                              (WOLFSSL_METHOD*) XMALLOC(sizeof(WOLFSSL_METHOD),
6178
0
                                                     heap, DYNAMIC_TYPE_METHOD);
6179
0
        (void)heap;
6180
0
        WOLFSSL_ENTER("wolfSSLv23_client_method_ex");
6181
0
        if (method) {
6182
0
    #if !defined(NO_SHA256) || defined(WOLFSSL_SHA384) || \
6183
0
        defined(WOLFSSL_SHA512)
6184
0
        #if defined(WOLFSSL_TLS13)
6185
0
            InitSSL_Method(method, MakeTLSv1_3());
6186
        #elif !defined(WOLFSSL_NO_TLS12)
6187
            InitSSL_Method(method, MakeTLSv1_2());
6188
        #elif !defined(NO_OLD_TLS)
6189
            InitSSL_Method(method, MakeTLSv1_1());
6190
        #endif
6191
    #else
6192
        #ifndef NO_OLD_TLS
6193
            InitSSL_Method(method, MakeTLSv1_1());
6194
        #endif
6195
    #endif
6196
0
    #if !defined(NO_OLD_TLS) || defined(WOLFSSL_TLS13)
6197
0
            method->downgrade = 1;
6198
0
    #endif
6199
0
        }
6200
0
        return method;
6201
0
    }
6202
6203
    /* please see note at top of README if you get an error from connect */
6204
    WOLFSSL_ABI
6205
    int wolfSSL_connect(WOLFSSL* ssl)
6206
    {
6207
    #if !(defined(WOLFSSL_NO_TLS12) && defined(NO_OLD_TLS) && \
6208
          defined(WOLFSSL_TLS13))
6209
        int neededState;
6210
        byte advanceState;
6211
    #endif
6212
        int ret = 0;
6213
6214
        (void)ret;
6215
6216
        #ifdef HAVE_ERRNO_H
6217
            errno = 0;
6218
        #endif
6219
6220
        if (ssl == NULL)
6221
            return BAD_FUNC_ARG;
6222
6223
    #if defined(OPENSSL_EXTRA) || defined(WOLFSSL_EITHER_SIDE)
6224
        if (ssl->options.side == WOLFSSL_NEITHER_END) {
6225
            ssl->error = InitSSL_Side(ssl, WOLFSSL_CLIENT_END);
6226
            if (ssl->error != WOLFSSL_SUCCESS) {
6227
                WOLFSSL_ERROR(ssl->error);
6228
                return WOLFSSL_FATAL_ERROR;
6229
            }
6230
            ssl->error = 0; /* expected to be zero here */
6231
        }
6232
6233
    #ifdef OPENSSL_EXTRA
6234
        if (ssl->CBIS != NULL) {
6235
            ssl->CBIS(ssl, WOLFSSL_ST_CONNECT, WOLFSSL_SUCCESS);
6236
            ssl->cbmode = WOLFSSL_CB_WRITE;
6237
        }
6238
    #endif
6239
    #endif /* OPENSSL_EXTRA || WOLFSSL_EITHER_SIDE */
6240
6241
    #if defined(WOLFSSL_NO_TLS12) && defined(NO_OLD_TLS) && \
6242
        defined(WOLFSSL_TLS13)
6243
        return wolfSSL_connect_TLSv13(ssl);
6244
    #else
6245
        #ifdef WOLFSSL_TLS13
6246
        if (ssl->options.tls1_3) {
6247
            WOLFSSL_MSG("TLS 1.3");
6248
            return wolfSSL_connect_TLSv13(ssl);
6249
        }
6250
        #endif
6251
6252
        WOLFSSL_MSG("TLS 1.2 or lower");
6253
        WOLFSSL_ENTER("wolfSSL_connect");
6254
6255
        /* make sure this wolfSSL object has arrays and rng setup. Protects
6256
         * case where the WOLFSSL object is reused via wolfSSL_clear() */
6257
        if ((ret = ReinitSSL(ssl, ssl->ctx, 0)) != 0) {
6258
            return ret;
6259
        }
6260
6261
#ifdef WOLFSSL_WOLFSENTRY_HOOKS
6262
        if ((ssl->ConnectFilter != NULL) &&
6263
            (ssl->options.connectState == CONNECT_BEGIN)) {
6264
            wolfSSL_netfilter_decision_t res;
6265
            if ((ssl->ConnectFilter(ssl, ssl->ConnectFilter_arg, &res) ==
6266
                 WOLFSSL_SUCCESS) &&
6267
                (res == WOLFSSL_NETFILTER_REJECT)) {
6268
                ssl->error = SOCKET_FILTERED_E;
6269
                WOLFSSL_ERROR(ssl->error);
6270
                return WOLFSSL_FATAL_ERROR;
6271
            }
6272
        }
6273
#endif /* WOLFSSL_WOLFSENTRY_HOOKS */
6274
6275
        if (ssl->options.side != WOLFSSL_CLIENT_END) {
6276
            ssl->error = SIDE_ERROR;
6277
            WOLFSSL_ERROR(ssl->error);
6278
            return WOLFSSL_FATAL_ERROR;
6279
        }
6280
6281
        #ifdef WOLFSSL_DTLS
6282
        if (ssl->version.major == DTLS_MAJOR) {
6283
            ssl->options.dtls   = 1;
6284
            ssl->options.tls    = 1;
6285
            ssl->options.tls1_1 = 1;
6286
            ssl->options.dtlsStateful = 1;
6287
        }
6288
        #endif
6289
6290
        /* fragOffset is non-zero when sending fragments. On the last
6291
         * fragment, fragOffset is zero again, and the state can be
6292
         * advanced. */
6293
        advanceState = ssl->fragOffset == 0 &&
6294
            (ssl->options.connectState == CONNECT_BEGIN ||
6295
             ssl->options.connectState == HELLO_AGAIN ||
6296
             (ssl->options.connectState >= FIRST_REPLY_DONE &&
6297
              ssl->options.connectState <= FIRST_REPLY_FOURTH));
6298
6299
#ifdef WOLFSSL_DTLS13
6300
        if (ssl->options.dtls && IsAtLeastTLSv1_3(ssl->version))
6301
            advanceState = advanceState && !ssl->dtls13SendingAckOrRtx;
6302
#endif /* WOLFSSL_DTLS13 */
6303
6304
        if (ssl->buffers.outputBuffer.length > 0
6305
        #ifdef WOLFSSL_ASYNC_CRYPT
6306
            /* do not send buffered or advance state if last error was an
6307
                async pending operation */
6308
            && ssl->error != WC_NO_ERR_TRACE(WC_PENDING_E)
6309
        #endif
6310
        ) {
6311
            ret = SendBuffered(ssl);
6312
            if (ret == 0) {
6313
                if (ssl->fragOffset == 0 && !ssl->options.buildingMsg) {
6314
                    if (advanceState) {
6315
                        ssl->options.connectState++;
6316
                        WOLFSSL_MSG("connect state: Advanced from last "
6317
                                    "buffered fragment send");
6318
                    #ifdef WOLFSSL_ASYNC_IO
6319
                        /* Cleanup async */
6320
                        FreeAsyncCtx(ssl, 0);
6321
                    #endif
6322
                    }
6323
                }
6324
                else {
6325
                    WOLFSSL_MSG("connect state: "
6326
                                "Not advanced, more fragments to send");
6327
                }
6328
            }
6329
            else {
6330
                ssl->error = ret;
6331
                WOLFSSL_ERROR(ssl->error);
6332
                return WOLFSSL_FATAL_ERROR;
6333
            }
6334
#ifdef WOLFSSL_DTLS13
6335
            if (ssl->options.dtls)
6336
                ssl->dtls13SendingAckOrRtx = 0;
6337
#endif /* WOLFSSL_DTLS13 */
6338
        }
6339
6340
        ret = RetrySendAlert(ssl);
6341
        if (ret != 0) {
6342
            ssl->error = ret;
6343
            WOLFSSL_ERROR(ssl->error);
6344
            return WOLFSSL_FATAL_ERROR;
6345
        }
6346
6347
        switch (ssl->options.connectState) {
6348
6349
        case CONNECT_BEGIN :
6350
            /* always send client hello first */
6351
            if ( (ssl->error = SendClientHello(ssl)) != 0) {
6352
                WOLFSSL_ERROR(ssl->error);
6353
                return WOLFSSL_FATAL_ERROR;
6354
            }
6355
            ssl->options.connectState = CLIENT_HELLO_SENT;
6356
            WOLFSSL_MSG("connect state: CLIENT_HELLO_SENT");
6357
            FALL_THROUGH;
6358
6359
        case CLIENT_HELLO_SENT :
6360
            neededState = ssl->options.resuming ? SERVER_FINISHED_COMPLETE :
6361
                                          SERVER_HELLODONE_COMPLETE;
6362
            #ifdef WOLFSSL_DTLS
6363
                /* In DTLS, when resuming, we can go straight to FINISHED,
6364
                 * or do a cookie exchange and then skip to FINISHED, assume
6365
                 * we need the cookie exchange first. */
6366
                if (IsDtlsNotSctpMode(ssl))
6367
                    neededState = SERVER_HELLOVERIFYREQUEST_COMPLETE;
6368
            #endif
6369
            /* get response */
6370
            WOLFSSL_MSG("Server state up to needed state.");
6371
            while (ssl->options.serverState < neededState) {
6372
                WOLFSSL_MSG("Progressing server state...");
6373
                #ifdef WOLFSSL_TLS13
6374
                    if (ssl->options.tls1_3)
6375
                        return wolfSSL_connect_TLSv13(ssl);
6376
                #endif
6377
                WOLFSSL_MSG("ProcessReply...");
6378
                if ( (ssl->error = ProcessReply(ssl)) < 0) {
6379
                    WOLFSSL_ERROR(ssl->error);
6380
                    return WOLFSSL_FATAL_ERROR;
6381
                }
6382
                /* if resumption failed, reset needed state */
6383
                else if (neededState == SERVER_FINISHED_COMPLETE) {
6384
                    if (!ssl->options.resuming) {
6385
                    #ifdef WOLFSSL_DTLS
6386
                        if (IsDtlsNotSctpMode(ssl))
6387
                            neededState = SERVER_HELLOVERIFYREQUEST_COMPLETE;
6388
                        else
6389
                    #endif
6390
                            neededState = SERVER_HELLODONE_COMPLETE;
6391
                    }
6392
                }
6393
                WOLFSSL_MSG("ProcessReply done.");
6394
6395
#ifdef WOLFSSL_DTLS13
6396
                if (ssl->options.dtls && IsAtLeastTLSv1_3(ssl->version)
6397
                    && ssl->dtls13Rtx.sendAcks == 1
6398
                    && ssl->options.seenUnifiedHdr) {
6399
                    /* we aren't negotiated the version yet, so we aren't sure
6400
                     * the other end can speak v1.3. On the other side we have
6401
                     * received a unified records, assuming that the
6402
                     * ServerHello got lost, we will send an empty ACK. In case
6403
                     * the server is a DTLS with version less than 1.3, it
6404
                     * should just ignore the message */
6405
                    ssl->dtls13Rtx.sendAcks = 0;
6406
                    if ((ssl->error = SendDtls13Ack(ssl)) < 0) {
6407
                        if (ssl->error == WC_NO_ERR_TRACE(WANT_WRITE))
6408
                            ssl->dtls13SendingAckOrRtx = 1;
6409
                        WOLFSSL_ERROR(ssl->error);
6410
                        return WOLFSSL_FATAL_ERROR;
6411
                    }
6412
                }
6413
#endif /* WOLFSSL_DTLS13 */
6414
            }
6415
6416
            ssl->options.connectState = HELLO_AGAIN;
6417
            WOLFSSL_MSG("connect state: HELLO_AGAIN");
6418
            FALL_THROUGH;
6419
6420
        case HELLO_AGAIN :
6421
6422
        #ifdef WOLFSSL_TLS13
6423
            if (ssl->options.tls1_3)
6424
                return wolfSSL_connect_TLSv13(ssl);
6425
        #endif
6426
6427
            #ifdef WOLFSSL_DTLS
6428
            if (ssl->options.serverState ==
6429
                    SERVER_HELLOVERIFYREQUEST_COMPLETE) {
6430
                if (IsDtlsNotSctpMode(ssl)) {
6431
                    /* re-init hashes, exclude first hello and verify request */
6432
                    if ((ssl->error = InitHandshakeHashes(ssl)) != 0) {
6433
                        WOLFSSL_ERROR(ssl->error);
6434
                        return WOLFSSL_FATAL_ERROR;
6435
                    }
6436
                    if ( (ssl->error = SendClientHello(ssl)) != 0) {
6437
                        WOLFSSL_ERROR(ssl->error);
6438
                        return WOLFSSL_FATAL_ERROR;
6439
                    }
6440
                }
6441
            }
6442
            #endif
6443
6444
            ssl->options.connectState = HELLO_AGAIN_REPLY;
6445
            WOLFSSL_MSG("connect state: HELLO_AGAIN_REPLY");
6446
            FALL_THROUGH;
6447
6448
        case HELLO_AGAIN_REPLY :
6449
            #ifdef WOLFSSL_DTLS
6450
                if (IsDtlsNotSctpMode(ssl)) {
6451
                    neededState = ssl->options.resuming ?
6452
                           SERVER_FINISHED_COMPLETE : SERVER_HELLODONE_COMPLETE;
6453
6454
                    /* get response */
6455
                    while (ssl->options.serverState < neededState) {
6456
                        if ( (ssl->error = ProcessReply(ssl)) < 0) {
6457
                            WOLFSSL_ERROR(ssl->error);
6458
                            return WOLFSSL_FATAL_ERROR;
6459
                        }
6460
                        /* if resumption failed, reset needed state */
6461
                        if (neededState == SERVER_FINISHED_COMPLETE) {
6462
                            if (!ssl->options.resuming)
6463
                                neededState = SERVER_HELLODONE_COMPLETE;
6464
                        }
6465
                    }
6466
                }
6467
            #endif
6468
6469
            ssl->options.connectState = FIRST_REPLY_DONE;
6470
            WOLFSSL_MSG("connect state: FIRST_REPLY_DONE");
6471
            FALL_THROUGH;
6472
6473
        case FIRST_REPLY_DONE :
6474
            if (ssl->options.certOnly)
6475
                return WOLFSSL_SUCCESS;
6476
            #if !defined(NO_CERTS) && !defined(WOLFSSL_NO_CLIENT_AUTH)
6477
                #ifdef WOLFSSL_TLS13
6478
                    if (ssl->options.tls1_3)
6479
                        return wolfSSL_connect_TLSv13(ssl);
6480
                #endif
6481
                if (ssl->options.sendVerify) {
6482
                    if ( (ssl->error = SendCertificate(ssl)) != 0) {
6483
                        wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6484
                        WOLFSSL_ERROR(ssl->error);
6485
                        return WOLFSSL_FATAL_ERROR;
6486
                    }
6487
                    WOLFSSL_MSG("sent: certificate");
6488
                }
6489
6490
            #endif
6491
            ssl->options.connectState = FIRST_REPLY_FIRST;
6492
            WOLFSSL_MSG("connect state: FIRST_REPLY_FIRST");
6493
            FALL_THROUGH;
6494
6495
        case FIRST_REPLY_FIRST :
6496
        #ifdef WOLFSSL_TLS13
6497
            if (ssl->options.tls1_3)
6498
                return wolfSSL_connect_TLSv13(ssl);
6499
        #endif
6500
            if (!ssl->options.resuming) {
6501
                if ( (ssl->error = SendClientKeyExchange(ssl)) != 0) {
6502
                    wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6503
#ifdef WOLFSSL_EXTRA_ALERTS
6504
                    if (ssl->error == WC_NO_ERR_TRACE(NO_PEER_KEY) ||
6505
                        ssl->error == WC_NO_ERR_TRACE(PSK_KEY_ERROR)) {
6506
                        SendAlert(ssl, alert_fatal, handshake_failure);
6507
                    }
6508
#endif
6509
                    WOLFSSL_ERROR(ssl->error);
6510
                    return WOLFSSL_FATAL_ERROR;
6511
                }
6512
                WOLFSSL_MSG("sent: client key exchange");
6513
            }
6514
6515
            ssl->options.connectState = FIRST_REPLY_SECOND;
6516
            WOLFSSL_MSG("connect state: FIRST_REPLY_SECOND");
6517
            FALL_THROUGH;
6518
6519
    #if !defined(WOLFSSL_NO_TLS12) || !defined(NO_OLD_TLS)
6520
        case FIRST_REPLY_SECOND :
6521
            /* CLIENT: Fail-safe for Server Authentication. */
6522
            if (!ssl->options.peerAuthGood) {
6523
                WOLFSSL_MSG("Server authentication did not happen");
6524
                ssl->error = NO_PEER_VERIFY;
6525
                return WOLFSSL_FATAL_ERROR;
6526
            }
6527
6528
            #if !defined(NO_CERTS) && !defined(WOLFSSL_NO_CLIENT_AUTH)
6529
                if (ssl->options.sendVerify) {
6530
                    if ( (ssl->error = SendCertificateVerify(ssl)) != 0) {
6531
                        wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6532
                        WOLFSSL_ERROR(ssl->error);
6533
                        return WOLFSSL_FATAL_ERROR;
6534
                    }
6535
                    WOLFSSL_MSG("sent: certificate verify");
6536
                }
6537
            #endif /* !NO_CERTS && !WOLFSSL_NO_CLIENT_AUTH */
6538
            ssl->options.connectState = FIRST_REPLY_THIRD;
6539
            WOLFSSL_MSG("connect state: FIRST_REPLY_THIRD");
6540
            FALL_THROUGH;
6541
6542
        case FIRST_REPLY_THIRD :
6543
            if ( (ssl->error = SendChangeCipher(ssl)) != 0) {
6544
                wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6545
                WOLFSSL_ERROR(ssl->error);
6546
                return WOLFSSL_FATAL_ERROR;
6547
            }
6548
            WOLFSSL_MSG("sent: change cipher spec");
6549
            ssl->options.connectState = FIRST_REPLY_FOURTH;
6550
            WOLFSSL_MSG("connect state: FIRST_REPLY_FOURTH");
6551
            FALL_THROUGH;
6552
6553
        case FIRST_REPLY_FOURTH :
6554
            if ( (ssl->error = SendFinished(ssl)) != 0) {
6555
                wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6556
                WOLFSSL_ERROR(ssl->error);
6557
                return WOLFSSL_FATAL_ERROR;
6558
            }
6559
            WOLFSSL_MSG("sent: finished");
6560
            ssl->options.connectState = FINISHED_DONE;
6561
            WOLFSSL_MSG("connect state: FINISHED_DONE");
6562
            FALL_THROUGH;
6563
6564
#ifdef WOLFSSL_DTLS13
6565
        case WAIT_FINISHED_ACK:
6566
            ssl->options.connectState = FINISHED_DONE;
6567
            FALL_THROUGH;
6568
#endif /* WOLFSSL_DTLS13 */
6569
6570
        case FINISHED_DONE :
6571
            /* get response */
6572
            while (ssl->options.serverState < SERVER_FINISHED_COMPLETE)
6573
                if ( (ssl->error = ProcessReply(ssl)) < 0) {
6574
                    WOLFSSL_ERROR(ssl->error);
6575
                    return WOLFSSL_FATAL_ERROR;
6576
                }
6577
6578
            ssl->options.connectState = SECOND_REPLY_DONE;
6579
            WOLFSSL_MSG("connect state: SECOND_REPLY_DONE");
6580
            FALL_THROUGH;
6581
6582
        case SECOND_REPLY_DONE:
6583
        #ifndef NO_HANDSHAKE_DONE_CB
6584
            if (ssl->hsDoneCb) {
6585
                int cbret = ssl->hsDoneCb(ssl, ssl->hsDoneCtx);
6586
                if (cbret < 0) {
6587
                    ssl->error = cbret;
6588
                    WOLFSSL_MSG("HandShake Done Cb don't continue error");
6589
                    return WOLFSSL_FATAL_ERROR;
6590
                }
6591
            }
6592
        #endif /* NO_HANDSHAKE_DONE_CB */
6593
6594
            if (!ssl->options.dtls) {
6595
                if (!ssl->options.keepResources) {
6596
                    FreeHandshakeResources(ssl);
6597
                }
6598
            }
6599
        #ifdef WOLFSSL_DTLS
6600
            else {
6601
                ssl->options.dtlsHsRetain = 1;
6602
            }
6603
        #endif /* WOLFSSL_DTLS */
6604
6605
        #if defined(WOLFSSL_ASYNC_CRYPT) && defined(HAVE_SECURE_RENEGOTIATION)
6606
            /* This may be necessary in async so that we don't try to
6607
             * renegotiate again */
6608
            if (ssl->secure_renegotiation &&
6609
                    ssl->secure_renegotiation->startScr) {
6610
                ssl->secure_renegotiation->startScr = 0;
6611
            }
6612
        #endif /* WOLFSSL_ASYNC_CRYPT && HAVE_SECURE_RENEGOTIATION */
6613
        #if defined(WOLFSSL_ASYNC_IO) && !defined(WOLFSSL_ASYNC_CRYPT)
6614
            /* Free the remaining async context if not using it for crypto */
6615
            FreeAsyncCtx(ssl, 1);
6616
        #endif
6617
6618
            ssl->error = 0; /* clear the error */
6619
6620
            WOLFSSL_LEAVE("wolfSSL_connect", WOLFSSL_SUCCESS);
6621
            return WOLFSSL_SUCCESS;
6622
    #endif /* !WOLFSSL_NO_TLS12 || !NO_OLD_TLS */
6623
6624
        default:
6625
            WOLFSSL_MSG("Unknown connect state ERROR");
6626
            return WOLFSSL_FATAL_ERROR; /* unknown connect state */
6627
        }
6628
    #endif /* !WOLFSSL_NO_TLS12 || !NO_OLD_TLS || !WOLFSSL_TLS13 */
6629
    }
6630
6631
#endif /* !NO_WOLFSSL_CLIENT && !NO_TLS */
6632
/* end client only parts */
6633
6634
/* server only parts */
6635
#if !defined(NO_WOLFSSL_SERVER) && !defined(NO_TLS)
6636
6637
    #if defined(OPENSSL_EXTRA) && !defined(NO_OLD_TLS)
6638
    WOLFSSL_METHOD* wolfSSLv2_server_method(void)
6639
    {
6640
        WOLFSSL_STUB("wolfSSLv2_server_method");
6641
        return 0;
6642
    }
6643
    #endif
6644
6645
    #if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS)
6646
    WOLFSSL_METHOD* wolfSSLv3_server_method(void)
6647
    {
6648
        return wolfSSLv3_server_method_ex(NULL);
6649
    }
6650
    WOLFSSL_METHOD* wolfSSLv3_server_method_ex(void* heap)
6651
    {
6652
        WOLFSSL_METHOD* method =
6653
                              (WOLFSSL_METHOD*) XMALLOC(sizeof(WOLFSSL_METHOD),
6654
                                                     heap, DYNAMIC_TYPE_METHOD);
6655
        (void)heap;
6656
        WOLFSSL_ENTER("wolfSSLv3_server_method_ex");
6657
        if (method) {
6658
            InitSSL_Method(method, MakeSSLv3());
6659
            method->side = WOLFSSL_SERVER_END;
6660
        }
6661
        return method;
6662
    }
6663
    #endif /* WOLFSSL_ALLOW_SSLV3 && !NO_OLD_TLS */
6664
6665
    WOLFSSL_METHOD* wolfSSLv23_server_method(void)
6666
0
    {
6667
0
        return wolfSSLv23_server_method_ex(NULL);
6668
0
    }
6669
6670
    WOLFSSL_METHOD* wolfSSLv23_server_method_ex(void* heap)
6671
0
    {
6672
0
        WOLFSSL_METHOD* method =
6673
0
                              (WOLFSSL_METHOD*) XMALLOC(sizeof(WOLFSSL_METHOD),
6674
0
                                                     heap, DYNAMIC_TYPE_METHOD);
6675
0
        (void)heap;
6676
0
        WOLFSSL_ENTER("wolfSSLv23_server_method_ex");
6677
0
        if (method) {
6678
0
    #if !defined(NO_SHA256) || defined(WOLFSSL_SHA384) || \
6679
0
        defined(WOLFSSL_SHA512)
6680
0
        #ifdef WOLFSSL_TLS13
6681
0
            InitSSL_Method(method, MakeTLSv1_3());
6682
        #elif !defined(WOLFSSL_NO_TLS12)
6683
            InitSSL_Method(method, MakeTLSv1_2());
6684
        #elif !defined(NO_OLD_TLS)
6685
            InitSSL_Method(method, MakeTLSv1_1());
6686
        #endif
6687
    #else
6688
        #ifndef NO_OLD_TLS
6689
            InitSSL_Method(method, MakeTLSv1_1());
6690
        #else
6691
            #error Must have SHA256, SHA384 or SHA512 enabled for TLS 1.2
6692
        #endif
6693
    #endif
6694
0
    #if !defined(NO_OLD_TLS) || defined(WOLFSSL_TLS13)
6695
0
            method->downgrade = 1;
6696
0
    #endif
6697
0
            method->side      = WOLFSSL_SERVER_END;
6698
0
        }
6699
0
        return method;
6700
0
    }
6701
6702
6703
    WOLFSSL_ABI
6704
    int wolfSSL_accept(WOLFSSL* ssl)
6705
0
    {
6706
0
#if !(defined(WOLFSSL_NO_TLS12) && defined(NO_OLD_TLS) && \
6707
0
    defined(WOLFSSL_TLS13))
6708
0
        word16 havePSK = 0;
6709
0
        word16 haveAnon = 0;
6710
0
        word16 haveMcast = 0;
6711
0
#endif
6712
0
        int ret = 0;
6713
6714
0
        (void)ret;
6715
6716
0
        if (ssl == NULL)
6717
0
            return WOLFSSL_FATAL_ERROR;
6718
6719
0
    #if defined(OPENSSL_EXTRA) || defined(WOLFSSL_EITHER_SIDE)
6720
0
        if (ssl->options.side == WOLFSSL_NEITHER_END) {
6721
0
            WOLFSSL_MSG("Setting WOLFSSL_SSL to be server side");
6722
0
            ssl->error = InitSSL_Side(ssl, WOLFSSL_SERVER_END);
6723
0
            if (ssl->error != WOLFSSL_SUCCESS) {
6724
0
                WOLFSSL_ERROR(ssl->error);
6725
0
                return WOLFSSL_FATAL_ERROR;
6726
0
            }
6727
0
            ssl->error = 0; /* expected to be zero here */
6728
0
        }
6729
0
    #endif /* OPENSSL_EXTRA || WOLFSSL_EITHER_SIDE */
6730
6731
#if defined(WOLFSSL_NO_TLS12) && defined(NO_OLD_TLS) && defined(WOLFSSL_TLS13)
6732
        return wolfSSL_accept_TLSv13(ssl);
6733
#else
6734
0
    #ifdef WOLFSSL_TLS13
6735
0
        if (ssl->options.tls1_3)
6736
0
            return wolfSSL_accept_TLSv13(ssl);
6737
0
    #endif
6738
0
        WOLFSSL_ENTER("wolfSSL_accept");
6739
6740
        /* make sure this wolfSSL object has arrays and rng setup. Protects
6741
         * case where the WOLFSSL object is reused via wolfSSL_clear() */
6742
0
        if ((ret = ReinitSSL(ssl, ssl->ctx, 0)) != 0) {
6743
0
            return ret;
6744
0
        }
6745
6746
#ifdef WOLFSSL_WOLFSENTRY_HOOKS
6747
        if ((ssl->AcceptFilter != NULL) &&
6748
            ((ssl->options.acceptState == ACCEPT_BEGIN)
6749
#ifdef HAVE_SECURE_RENEGOTIATION
6750
             || (ssl->options.acceptState == ACCEPT_BEGIN_RENEG)
6751
#endif
6752
                ))
6753
        {
6754
            wolfSSL_netfilter_decision_t res;
6755
            if ((ssl->AcceptFilter(ssl, ssl->AcceptFilter_arg, &res) ==
6756
                 WOLFSSL_SUCCESS) &&
6757
                (res == WOLFSSL_NETFILTER_REJECT)) {
6758
                ssl->error = SOCKET_FILTERED_E;
6759
                WOLFSSL_ERROR(ssl->error);
6760
                return WOLFSSL_FATAL_ERROR;
6761
            }
6762
        }
6763
#endif /* WOLFSSL_WOLFSENTRY_HOOKS */
6764
6765
0
        #ifdef HAVE_ERRNO_H
6766
0
            errno = 0;
6767
0
        #endif
6768
6769
        #ifndef NO_PSK
6770
            havePSK = ssl->options.havePSK;
6771
        #endif
6772
0
        (void)havePSK;
6773
6774
        #ifdef HAVE_ANON
6775
            haveAnon = ssl->options.useAnon;
6776
        #endif
6777
0
        (void)haveAnon;
6778
6779
        #ifdef WOLFSSL_MULTICAST
6780
            haveMcast = ssl->options.haveMcast;
6781
        #endif
6782
0
        (void)haveMcast;
6783
6784
0
        if (ssl->options.side != WOLFSSL_SERVER_END) {
6785
0
            ssl->error = SIDE_ERROR;
6786
0
            WOLFSSL_ERROR(ssl->error);
6787
0
            return WOLFSSL_FATAL_ERROR;
6788
0
        }
6789
6790
0
    #ifndef NO_CERTS
6791
        /* in case used set_accept_state after init */
6792
0
        if (!havePSK && !haveAnon && !haveMcast) {
6793
0
        #ifdef WOLFSSL_CERT_SETUP_CB
6794
0
            if (ssl->ctx->certSetupCb != NULL) {
6795
0
                WOLFSSL_MSG("CertSetupCb set. server cert and "
6796
0
                            "key not checked");
6797
0
            }
6798
0
            else
6799
0
        #endif
6800
0
            {
6801
0
                if (!ssl->buffers.certificate ||
6802
0
                    !ssl->buffers.certificate->buffer) {
6803
6804
0
                    WOLFSSL_MSG("accept error: server cert required");
6805
0
                    ssl->error = NO_PRIVATE_KEY;
6806
0
                    WOLFSSL_ERROR(ssl->error);
6807
0
                    return WOLFSSL_FATAL_ERROR;
6808
0
                }
6809
6810
0
                if (!ssl->buffers.key || !ssl->buffers.key->buffer) {
6811
                    /* allow no private key if using existing key */
6812
0
                #ifdef WOLF_PRIVATE_KEY_ID
6813
0
                    if (ssl->devId != INVALID_DEVID
6814
                    #ifdef HAVE_PK_CALLBACKS
6815
                        || wolfSSL_CTX_IsPrivatePkSet(ssl->ctx)
6816
                    #endif
6817
0
                    ) {
6818
0
                        WOLFSSL_MSG("Allowing no server private key "
6819
0
                                    "(external)");
6820
0
                    }
6821
0
                    else
6822
0
                #endif
6823
0
                    {
6824
0
                        WOLFSSL_MSG("accept error: server key required");
6825
0
                        ssl->error = NO_PRIVATE_KEY;
6826
0
                        WOLFSSL_ERROR(ssl->error);
6827
0
                        return WOLFSSL_FATAL_ERROR;
6828
0
                    }
6829
0
                }
6830
0
            }
6831
0
        }
6832
0
    #endif
6833
6834
    #ifdef WOLFSSL_DTLS
6835
        if (ssl->version.major == DTLS_MAJOR) {
6836
            ssl->options.dtls   = 1;
6837
            ssl->options.tls    = 1;
6838
            ssl->options.tls1_1 = 1;
6839
            if (!IsDtlsNotSctpMode(ssl) || IsSCR(ssl))
6840
                ssl->options.dtlsStateful = 1;
6841
        }
6842
    #endif
6843
6844
0
        if (ssl->buffers.outputBuffer.length > 0
6845
        #ifdef WOLFSSL_ASYNC_CRYPT
6846
            /* do not send buffered or advance state if last error was an
6847
                async pending operation */
6848
            && ssl->error != WC_NO_ERR_TRACE(WC_PENDING_E)
6849
        #endif
6850
0
        ) {
6851
0
            ret = SendBuffered(ssl);
6852
0
            if (ret == 0) {
6853
                /* fragOffset is non-zero when sending fragments. On the last
6854
                 * fragment, fragOffset is zero again, and the state can be
6855
                 * advanced. */
6856
0
                if (ssl->fragOffset == 0 && !ssl->options.buildingMsg) {
6857
0
                    if (ssl->options.acceptState == ACCEPT_FIRST_REPLY_DONE ||
6858
0
                        ssl->options.acceptState == SERVER_HELLO_SENT ||
6859
0
                        ssl->options.acceptState == CERT_SENT ||
6860
0
                        ssl->options.acceptState == CERT_STATUS_SENT ||
6861
0
                        ssl->options.acceptState == KEY_EXCHANGE_SENT ||
6862
0
                        ssl->options.acceptState == CERT_REQ_SENT ||
6863
0
                        ssl->options.acceptState == ACCEPT_SECOND_REPLY_DONE ||
6864
0
                        ssl->options.acceptState == TICKET_SENT ||
6865
0
                        ssl->options.acceptState == CHANGE_CIPHER_SENT) {
6866
0
                        ssl->options.acceptState++;
6867
0
                        WOLFSSL_MSG("accept state: Advanced from last "
6868
0
                                    "buffered fragment send");
6869
0
                    #ifdef WOLFSSL_ASYNC_IO
6870
                        /* Cleanup async */
6871
0
                        FreeAsyncCtx(ssl, 0);
6872
0
                    #endif
6873
0
                    }
6874
0
                }
6875
0
                else {
6876
0
                    WOLFSSL_MSG("accept state: "
6877
0
                                "Not advanced, more fragments to send");
6878
0
                }
6879
0
            }
6880
0
            else {
6881
0
                ssl->error = ret;
6882
0
                WOLFSSL_ERROR(ssl->error);
6883
0
                return WOLFSSL_FATAL_ERROR;
6884
0
            }
6885
#ifdef WOLFSSL_DTLS13
6886
            if (ssl->options.dtls)
6887
                ssl->dtls13SendingAckOrRtx = 0;
6888
#endif /* WOLFSSL_DTLS13 */
6889
0
        }
6890
6891
0
        ret = RetrySendAlert(ssl);
6892
0
        if (ret != 0) {
6893
0
            ssl->error = ret;
6894
0
            WOLFSSL_ERROR(ssl->error);
6895
0
            return WOLFSSL_FATAL_ERROR;
6896
0
        }
6897
6898
0
        switch (ssl->options.acceptState) {
6899
6900
0
        case ACCEPT_BEGIN :
6901
#ifdef HAVE_SECURE_RENEGOTIATION
6902
        case ACCEPT_BEGIN_RENEG:
6903
#endif
6904
            /* get response */
6905
0
            while (ssl->options.clientState < CLIENT_HELLO_COMPLETE)
6906
0
                if ( (ssl->error = ProcessReply(ssl)) < 0) {
6907
0
                    WOLFSSL_ERROR(ssl->error);
6908
0
                    return WOLFSSL_FATAL_ERROR;
6909
0
                }
6910
0
#ifdef WOLFSSL_TLS13
6911
0
            ssl->options.acceptState = ACCEPT_CLIENT_HELLO_DONE;
6912
0
            WOLFSSL_MSG("accept state ACCEPT_CLIENT_HELLO_DONE");
6913
0
            FALL_THROUGH;
6914
6915
0
        case ACCEPT_CLIENT_HELLO_DONE :
6916
0
            if (ssl->options.tls1_3) {
6917
0
                return wolfSSL_accept_TLSv13(ssl);
6918
0
            }
6919
0
#endif
6920
6921
0
            ssl->options.acceptState = ACCEPT_FIRST_REPLY_DONE;
6922
0
            WOLFSSL_MSG("accept state ACCEPT_FIRST_REPLY_DONE");
6923
0
            FALL_THROUGH;
6924
6925
0
        case ACCEPT_FIRST_REPLY_DONE :
6926
0
            if (ssl->options.returnOnGoodCh) {
6927
                /* Higher level in stack wants us to return. Simulate a
6928
                 * WANT_WRITE to accomplish this. */
6929
0
                ssl->error = WANT_WRITE;
6930
0
                return WOLFSSL_FATAL_ERROR;
6931
0
            }
6932
0
            if ( (ssl->error = SendServerHello(ssl)) != 0) {
6933
0
                wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6934
0
                WOLFSSL_ERROR(ssl->error);
6935
0
                return WOLFSSL_FATAL_ERROR;
6936
0
            }
6937
0
            ssl->options.acceptState = SERVER_HELLO_SENT;
6938
0
            WOLFSSL_MSG("accept state SERVER_HELLO_SENT");
6939
0
            FALL_THROUGH;
6940
6941
0
        case SERVER_HELLO_SENT :
6942
0
        #ifdef WOLFSSL_TLS13
6943
0
            if (ssl->options.tls1_3) {
6944
0
                return wolfSSL_accept_TLSv13(ssl);
6945
0
            }
6946
0
        #endif
6947
0
            #ifndef NO_CERTS
6948
0
                if (!ssl->options.resuming)
6949
0
                    if ( (ssl->error = SendCertificate(ssl)) != 0) {
6950
0
                        wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6951
0
                        WOLFSSL_ERROR(ssl->error);
6952
0
                        return WOLFSSL_FATAL_ERROR;
6953
0
                    }
6954
0
            #endif
6955
0
            ssl->options.acceptState = CERT_SENT;
6956
0
            WOLFSSL_MSG("accept state CERT_SENT");
6957
0
            FALL_THROUGH;
6958
6959
0
        case CERT_SENT :
6960
0
            #ifndef NO_CERTS
6961
0
            if (!ssl->options.resuming)
6962
0
                if ( (ssl->error = SendCertificateStatus(ssl)) != 0) {
6963
0
                    wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6964
0
                    WOLFSSL_ERROR(ssl->error);
6965
0
                    return WOLFSSL_FATAL_ERROR;
6966
0
                }
6967
0
            #endif
6968
0
            ssl->options.acceptState = CERT_STATUS_SENT;
6969
0
            WOLFSSL_MSG("accept state CERT_STATUS_SENT");
6970
0
            FALL_THROUGH;
6971
6972
0
        case CERT_STATUS_SENT :
6973
0
        #ifdef WOLFSSL_TLS13
6974
0
            if (ssl->options.tls1_3) {
6975
0
                return wolfSSL_accept_TLSv13(ssl);
6976
0
            }
6977
0
        #endif
6978
0
            if (!ssl->options.resuming)
6979
0
                if ( (ssl->error = SendServerKeyExchange(ssl)) != 0) {
6980
0
                    wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6981
0
                    WOLFSSL_ERROR(ssl->error);
6982
0
                    return WOLFSSL_FATAL_ERROR;
6983
0
                }
6984
0
            ssl->options.acceptState = KEY_EXCHANGE_SENT;
6985
0
            WOLFSSL_MSG("accept state KEY_EXCHANGE_SENT");
6986
0
            FALL_THROUGH;
6987
6988
0
        case KEY_EXCHANGE_SENT :
6989
0
            #ifndef NO_CERTS
6990
0
                if (!ssl->options.resuming) {
6991
0
                    if (ssl->options.verifyPeer) {
6992
0
                        if ( (ssl->error = SendCertificateRequest(ssl)) != 0) {
6993
0
                            wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
6994
0
                            WOLFSSL_ERROR(ssl->error);
6995
0
                            return WOLFSSL_FATAL_ERROR;
6996
0
                        }
6997
0
                    }
6998
0
                    else {
6999
                        /* SERVER: Peer auth good if not verifying client. */
7000
0
                        ssl->options.peerAuthGood = 1;
7001
0
                    }
7002
0
                }
7003
0
            #endif
7004
0
            ssl->options.acceptState = CERT_REQ_SENT;
7005
0
            WOLFSSL_MSG("accept state CERT_REQ_SENT");
7006
0
            FALL_THROUGH;
7007
7008
0
        case CERT_REQ_SENT :
7009
0
            if (!ssl->options.resuming)
7010
0
                if ( (ssl->error = SendServerHelloDone(ssl)) != 0) {
7011
0
                    wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
7012
0
                    WOLFSSL_ERROR(ssl->error);
7013
0
                    return WOLFSSL_FATAL_ERROR;
7014
0
                }
7015
0
            ssl->options.acceptState = SERVER_HELLO_DONE;
7016
0
            WOLFSSL_MSG("accept state SERVER_HELLO_DONE");
7017
0
            FALL_THROUGH;
7018
7019
0
        case SERVER_HELLO_DONE :
7020
0
            if (!ssl->options.resuming) {
7021
0
                while (ssl->options.clientState < CLIENT_FINISHED_COMPLETE)
7022
0
                    if ( (ssl->error = ProcessReply(ssl)) < 0) {
7023
0
                        WOLFSSL_ERROR(ssl->error);
7024
0
                        return WOLFSSL_FATAL_ERROR;
7025
0
                    }
7026
0
            }
7027
0
            ssl->options.acceptState = ACCEPT_SECOND_REPLY_DONE;
7028
0
            WOLFSSL_MSG("accept state  ACCEPT_SECOND_REPLY_DONE");
7029
0
            FALL_THROUGH;
7030
7031
0
        case ACCEPT_SECOND_REPLY_DONE :
7032
0
        #ifndef NO_CERTS
7033
            /* SERVER: When not resuming and verifying peer but no certificate
7034
             * received and not failing when not received then peer auth good.
7035
             */
7036
0
            if (!ssl->options.resuming && ssl->options.verifyPeer &&
7037
0
                !ssl->options.havePeerCert && !ssl->options.failNoCert) {
7038
0
                ssl->options.peerAuthGood = 1;
7039
0
            }
7040
0
        #endif /* !NO_CERTS  */
7041
        #ifdef WOLFSSL_NO_CLIENT_AUTH
7042
            if (!ssl->options.resuming) {
7043
                ssl->options.peerAuthGood = 1;
7044
            }
7045
        #endif
7046
7047
0
#ifdef HAVE_SESSION_TICKET
7048
0
            if (ssl->options.createTicket && !ssl->options.noTicketTls12) {
7049
0
                if ( (ssl->error = SendTicket(ssl)) != 0) {
7050
0
                    wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
7051
0
                    WOLFSSL_MSG("Thought we need ticket but failed");
7052
0
                    WOLFSSL_ERROR(ssl->error);
7053
0
                    return WOLFSSL_FATAL_ERROR;
7054
0
                }
7055
0
            }
7056
0
#endif /* HAVE_SESSION_TICKET */
7057
0
            ssl->options.acceptState = TICKET_SENT;
7058
0
            WOLFSSL_MSG("accept state  TICKET_SENT");
7059
0
            FALL_THROUGH;
7060
7061
0
        case TICKET_SENT:
7062
            /* SERVER: Fail-safe for CLient Authentication. */
7063
0
            if (!ssl->options.peerAuthGood) {
7064
0
                WOLFSSL_MSG("Client authentication did not happen");
7065
0
                return WOLFSSL_FATAL_ERROR;
7066
0
            }
7067
7068
0
            if ( (ssl->error = SendChangeCipher(ssl)) != 0) {
7069
0
                wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
7070
0
                WOLFSSL_ERROR(ssl->error);
7071
0
                return WOLFSSL_FATAL_ERROR;
7072
0
            }
7073
0
            ssl->options.acceptState = CHANGE_CIPHER_SENT;
7074
0
            WOLFSSL_MSG("accept state  CHANGE_CIPHER_SENT");
7075
0
            FALL_THROUGH;
7076
7077
0
        case CHANGE_CIPHER_SENT :
7078
0
            if ( (ssl->error = SendFinished(ssl)) != 0) {
7079
0
                wolfssl_local_MaybeCheckAlertOnErr(ssl, ssl->error);
7080
0
                WOLFSSL_ERROR(ssl->error);
7081
0
                return WOLFSSL_FATAL_ERROR;
7082
0
            }
7083
7084
0
            ssl->options.acceptState = ACCEPT_FINISHED_DONE;
7085
0
            WOLFSSL_MSG("accept state ACCEPT_FINISHED_DONE");
7086
0
            FALL_THROUGH;
7087
7088
0
        case ACCEPT_FINISHED_DONE :
7089
0
            if (ssl->options.resuming) {
7090
0
                while (ssl->options.clientState < CLIENT_FINISHED_COMPLETE) {
7091
0
                    if ( (ssl->error = ProcessReply(ssl)) < 0) {
7092
0
                        WOLFSSL_ERROR(ssl->error);
7093
0
                        return WOLFSSL_FATAL_ERROR;
7094
0
                    }
7095
0
                }
7096
0
            }
7097
0
            ssl->options.acceptState = ACCEPT_THIRD_REPLY_DONE;
7098
0
            WOLFSSL_MSG("accept state ACCEPT_THIRD_REPLY_DONE");
7099
0
            FALL_THROUGH;
7100
7101
0
        case ACCEPT_THIRD_REPLY_DONE :
7102
0
#ifndef NO_HANDSHAKE_DONE_CB
7103
0
            if (ssl->hsDoneCb) {
7104
0
                int cbret = ssl->hsDoneCb(ssl, ssl->hsDoneCtx);
7105
0
                if (cbret < 0) {
7106
0
                    ssl->error = cbret;
7107
0
                    WOLFSSL_MSG("HandShake Done Cb don't continue error");
7108
0
                    return WOLFSSL_FATAL_ERROR;
7109
0
                }
7110
0
            }
7111
0
#endif /* NO_HANDSHAKE_DONE_CB */
7112
7113
0
            if (!ssl->options.dtls) {
7114
0
                if (!ssl->options.keepResources) {
7115
0
                    FreeHandshakeResources(ssl);
7116
0
                }
7117
0
            }
7118
#ifdef WOLFSSL_DTLS
7119
            else {
7120
                ssl->options.dtlsHsRetain = 1;
7121
            }
7122
#endif /* WOLFSSL_DTLS */
7123
7124
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(HAVE_SECURE_RENEGOTIATION)
7125
            /* This may be necessary in async so that we don't try to
7126
             * renegotiate again */
7127
            if (ssl->secure_renegotiation &&
7128
                    ssl->secure_renegotiation->startScr) {
7129
                ssl->secure_renegotiation->startScr = 0;
7130
            }
7131
#endif /* WOLFSSL_ASYNC_CRYPT && HAVE_SECURE_RENEGOTIATION */
7132
0
#if defined(WOLFSSL_ASYNC_IO) && !defined(WOLFSSL_ASYNC_CRYPT)
7133
            /* Free the remaining async context if not using it for crypto */
7134
0
            FreeAsyncCtx(ssl, 1);
7135
0
#endif
7136
7137
#if defined(WOLFSSL_SESSION_EXPORT) && defined(WOLFSSL_DTLS)
7138
            if (ssl->dtls_export) {
7139
                if ((ssl->error = wolfSSL_send_session(ssl)) != 0) {
7140
                    WOLFSSL_MSG("Export DTLS session error");
7141
                    WOLFSSL_ERROR(ssl->error);
7142
                    return WOLFSSL_FATAL_ERROR;
7143
                }
7144
            }
7145
#endif
7146
0
            ssl->error = 0; /* clear the error */
7147
7148
0
            WOLFSSL_LEAVE("wolfSSL_accept", WOLFSSL_SUCCESS);
7149
0
            return WOLFSSL_SUCCESS;
7150
7151
0
        default:
7152
0
            WOLFSSL_MSG("Unknown accept state ERROR");
7153
0
            return WOLFSSL_FATAL_ERROR;
7154
0
        }
7155
0
#endif /* !WOLFSSL_NO_TLS12 */
7156
0
    }
7157
7158
#endif /* !NO_WOLFSSL_SERVER && !NO_TLS */
7159
/* end server only parts */
7160
7161
7162
#if defined(WOLFSSL_DTLS) && !defined(NO_WOLFSSL_SERVER)
7163
struct chGoodDisableReadCbCtx {
7164
    ClientHelloGoodCb userCb;
7165
    void*             userCtx;
7166
};
7167
7168
static int chGoodDisableReadCB(WOLFSSL* ssl, void* ctx)
7169
{
7170
    struct chGoodDisableReadCbCtx* cb = (struct chGoodDisableReadCbCtx*)ctx;
7171
    int ret = 0;
7172
    if (cb->userCb != NULL)
7173
        ret = cb->userCb(ssl, cb->userCtx);
7174
    if (ret >= 0)
7175
        wolfSSL_SSLDisableRead(ssl);
7176
    return ret;
7177
}
7178
7179
/**
7180
 * Statelessly listen for a connection
7181
 * @param ssl The ssl object to use for listening to connections
7182
 * @return WOLFSSL_SUCCESS - ClientHello containing a valid cookie was received
7183
 *                           The connection can be continued with wolfSSL_accept
7184
 *         WOLFSSL_FAILURE - The I/O layer returned WANT_READ. This is either
7185
 *                           because there is no data to read and we are using
7186
 *                           non-blocking sockets or we sent a cookie request
7187
 *                           and we are waiting for a reply. The user should
7188
 *                           call wolfDTLS_accept_stateless again after data
7189
 *                           becomes available in the I/O layer.
7190
 *         WOLFSSL_FATAL_ERROR - A fatal error occurred. The ssl object should
7191
 *                           be free'd and allocated again to continue.
7192
 */
7193
int wolfDTLS_accept_stateless(WOLFSSL* ssl)
7194
{
7195
    byte disableRead;
7196
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR);
7197
    struct chGoodDisableReadCbCtx cb;
7198
7199
    WOLFSSL_ENTER("wolfDTLS_SetChGoodCb");
7200
7201
    if (ssl == NULL)
7202
        return WOLFSSL_FATAL_ERROR;
7203
7204
    /* Save this to restore it later */
7205
    disableRead = (byte)ssl->options.disableRead;
7206
    cb.userCb = ssl->chGoodCb;
7207
    cb.userCtx = ssl->chGoodCtx;
7208
7209
    /* Register our own callback so that we can disable reading */
7210
    if (wolfDTLS_SetChGoodCb(ssl, chGoodDisableReadCB, &cb) != WOLFSSL_SUCCESS)
7211
        return WOLFSSL_FATAL_ERROR;
7212
7213
    ssl->options.returnOnGoodCh = 1;
7214
    ret = wolfSSL_accept(ssl);
7215
    ssl->options.returnOnGoodCh = 0;
7216
    /* restore user options */
7217
    ssl->options.disableRead = disableRead;
7218
    (void)wolfDTLS_SetChGoodCb(ssl, cb.userCb, cb.userCtx);
7219
    if (ret == WOLFSSL_SUCCESS) {
7220
        WOLFSSL_MSG("should not happen. maybe the user called "
7221
                    "wolfDTLS_accept_stateless instead of wolfSSL_accept");
7222
    }
7223
    else if (ssl->error == WC_NO_ERR_TRACE(WANT_READ) ||
7224
             ssl->error == WC_NO_ERR_TRACE(WANT_WRITE)) {
7225
        ssl->error = 0;
7226
        if (ssl->options.dtlsStateful)
7227
            ret = WOLFSSL_SUCCESS;
7228
        else
7229
            ret = WOLFSSL_FAILURE;
7230
    }
7231
    else {
7232
        ret = WOLFSSL_FATAL_ERROR;
7233
    }
7234
    return ret;
7235
}
7236
7237
int wolfDTLS_SetChGoodCb(WOLFSSL* ssl, ClientHelloGoodCb cb, void* user_ctx)
7238
{
7239
    WOLFSSL_ENTER("wolfDTLS_SetChGoodCb");
7240
7241
    if (ssl == NULL)
7242
        return BAD_FUNC_ARG;
7243
7244
    ssl->chGoodCb  = cb;
7245
    ssl->chGoodCtx = user_ctx;
7246
7247
    return WOLFSSL_SUCCESS;
7248
}
7249
#endif
7250
7251
#ifndef NO_HANDSHAKE_DONE_CB
7252
7253
int wolfSSL_SetHsDoneCb(WOLFSSL* ssl, HandShakeDoneCb cb, void* user_ctx)
7254
0
{
7255
0
    WOLFSSL_ENTER("wolfSSL_SetHsDoneCb");
7256
7257
0
    if (ssl == NULL)
7258
0
        return BAD_FUNC_ARG;
7259
7260
0
    ssl->hsDoneCb  = cb;
7261
0
    ssl->hsDoneCtx = user_ctx;
7262
7263
0
    return WOLFSSL_SUCCESS;
7264
0
}
7265
7266
#endif /* NO_HANDSHAKE_DONE_CB */
7267
7268
WOLFSSL_ABI
7269
int wolfSSL_Cleanup(void)
7270
20.3k
{
7271
20.3k
    int ret = WOLFSSL_SUCCESS; /* Only the first error will be returned */
7272
20.3k
    int release = 0;
7273
20.3k
#if !defined(NO_SESSION_CACHE)
7274
20.3k
    int i;
7275
20.3k
    int j;
7276
20.3k
#endif
7277
7278
20.3k
    WOLFSSL_ENTER("wolfSSL_Cleanup");
7279
7280
#ifndef WOLFSSL_MUTEX_INITIALIZER
7281
    if (inits_count_mutex_valid == 1) {
7282
#endif
7283
20.3k
        if (wc_LockMutex(&inits_count_mutex) != 0) {
7284
0
            WOLFSSL_MSG("Bad Lock Mutex count");
7285
0
            return BAD_MUTEX_E;
7286
0
        }
7287
#ifndef WOLFSSL_MUTEX_INITIALIZER
7288
    }
7289
#endif
7290
7291
20.3k
    if (initRefCount > 0) {
7292
4.79k
        initRefCount = initRefCount - 1;
7293
4.79k
        if (initRefCount == 0)
7294
4.79k
            release = 1;
7295
4.79k
    }
7296
7297
#ifndef WOLFSSL_MUTEX_INITIALIZER
7298
    if (inits_count_mutex_valid == 1) {
7299
#endif
7300
20.3k
        wc_UnLockMutex(&inits_count_mutex);
7301
#ifndef WOLFSSL_MUTEX_INITIALIZER
7302
    }
7303
#endif
7304
7305
20.3k
    if (!release)
7306
15.5k
        return ret;
7307
7308
#if defined(WOLFSSL_SYS_CRYPTO_POLICY)
7309
    wolfSSL_crypto_policy_disable();
7310
#endif /* WOLFSSL_SYS_CRYPTO_POLICY */
7311
7312
4.79k
#ifdef OPENSSL_EXTRA
7313
4.79k
    wolfSSL_BN_free_one();
7314
4.79k
#endif
7315
7316
4.79k
#ifndef NO_SESSION_CACHE
7317
    #ifdef ENABLE_SESSION_CACHE_ROW_LOCK
7318
    for (i = 0; i < SESSION_ROWS; ++i) {
7319
        if ((SessionCache[i].lock_valid == 1) &&
7320
            (wc_FreeRwLock(&SessionCache[i].row_lock) != 0)) {
7321
            if (ret == WOLFSSL_SUCCESS)
7322
                ret = BAD_MUTEX_E;
7323
        }
7324
        SessionCache[i].lock_valid = 0;
7325
    }
7326
    #else
7327
4.79k
    if ((session_lock_valid == 1) && (wc_FreeRwLock(&session_lock) != 0)) {
7328
0
        if (ret == WOLFSSL_SUCCESS)
7329
0
            ret = BAD_MUTEX_E;
7330
0
    }
7331
4.79k
    session_lock_valid = 0;
7332
4.79k
    #endif
7333
57.5k
    for (i = 0; i < SESSION_ROWS; i++) {
7334
211k
        for (j = 0; j < SESSIONS_PER_ROW; j++) {
7335
    #ifdef SESSION_CACHE_DYNAMIC_MEM
7336
            if (SessionCache[i].Sessions[j]) {
7337
                EvictSessionFromCache(SessionCache[i].Sessions[j]);
7338
                XFREE(SessionCache[i].Sessions[j], SessionCache[i].heap,
7339
                      DYNAMIC_TYPE_SESSION);
7340
                SessionCache[i].Sessions[j] = NULL;
7341
            }
7342
    #else
7343
158k
            EvictSessionFromCache(&SessionCache[i].Sessions[j]);
7344
158k
    #endif
7345
158k
        }
7346
52.7k
    }
7347
4.79k
    #ifndef NO_CLIENT_CACHE
7348
    #ifndef WOLFSSL_MUTEX_INITIALIZER
7349
    if ((clisession_mutex_valid == 1) &&
7350
        (wc_FreeMutex(&clisession_mutex) != 0)) {
7351
        if (ret == WOLFSSL_SUCCESS)
7352
            ret = BAD_MUTEX_E;
7353
    }
7354
    clisession_mutex_valid = 0;
7355
    #endif
7356
4.79k
    #endif
7357
4.79k
#endif /* !NO_SESSION_CACHE */
7358
7359
#if !defined(WOLFSSL_MUTEX_INITIALIZER) && \
7360
      !WOLFSSL_CLEANUP_THREADSAFE_BY_ATOMIC_OPS
7361
    if ((inits_count_mutex_valid == 1) &&
7362
            (wc_FreeMutex(&inits_count_mutex) != 0)) {
7363
        if (ret == WOLFSSL_SUCCESS)
7364
            ret = BAD_MUTEX_E;
7365
    }
7366
    inits_count_mutex_valid = 0;
7367
#endif
7368
7369
4.79k
#ifdef OPENSSL_EXTRA
7370
4.79k
    wolfSSL_RAND_Cleanup();
7371
4.79k
#endif
7372
7373
4.79k
    if (wolfCrypt_Cleanup() != 0) {
7374
0
        WOLFSSL_MSG("Error with wolfCrypt_Cleanup call");
7375
0
        if (ret == WOLFSSL_SUCCESS)
7376
0
            ret = WC_CLEANUP_E;
7377
0
    }
7378
7379
#if FIPS_VERSION_GE(5,1)
7380
    if (wolfCrypt_SetPrivateKeyReadEnable_fips(0, WC_KEYTYPE_ALL) < 0) {
7381
        if (ret == WOLFSSL_SUCCESS)
7382
            ret = WC_CLEANUP_E;
7383
    }
7384
#endif
7385
7386
4.79k
#ifdef HAVE_GLOBAL_RNG
7387
#ifndef WOLFSSL_MUTEX_INITIALIZER
7388
    if ((globalRNGMutex_valid == 1) && (wc_FreeMutex(&globalRNGMutex) != 0)) {
7389
        if (ret == WOLFSSL_SUCCESS)
7390
            ret = BAD_MUTEX_E;
7391
    }
7392
    globalRNGMutex_valid = 0;
7393
#endif /* !WOLFSSL_MUTEX_INITIALIZER */
7394
7395
4.79k
    #if defined(OPENSSL_EXTRA) && defined(HAVE_HASHDRBG)
7396
4.79k
    wolfSSL_FIPS_drbg_free(gDrbgDefCtx);
7397
4.79k
    gDrbgDefCtx = NULL;
7398
4.79k
    #endif
7399
4.79k
#endif
7400
7401
4.79k
#ifdef HAVE_EX_DATA_CRYPTO
7402
4.79k
    crypto_ex_cb_free(crypto_ex_cb_ctx_session);
7403
4.79k
    crypto_ex_cb_ctx_session = NULL;
7404
4.79k
#endif
7405
7406
#ifdef WOLFSSL_MEM_FAIL_COUNT
7407
    wc_MemFailCount_Free();
7408
#endif
7409
7410
4.79k
    return ret;
7411
20.3k
}
7412
7413
7414
/* call before SSL_connect, if verifying will add name check to
7415
   date check and signature check */
7416
WOLFSSL_ABI
7417
int wolfSSL_check_domain_name(WOLFSSL* ssl, const char* dn)
7418
0
{
7419
0
    WOLFSSL_ENTER("wolfSSL_check_domain_name");
7420
7421
0
    if (ssl == NULL || dn == NULL) {
7422
0
        WOLFSSL_MSG("Bad function argument: NULL");
7423
0
        return WOLFSSL_FAILURE;
7424
0
    }
7425
7426
0
    if (ssl->buffers.domainName.buffer)
7427
0
        XFREE(ssl->buffers.domainName.buffer, ssl->heap, DYNAMIC_TYPE_DOMAIN);
7428
7429
0
    ssl->buffers.domainName.length = (word32)XSTRLEN(dn);
7430
0
    ssl->buffers.domainName.buffer = (byte*)XMALLOC(
7431
0
            ssl->buffers.domainName.length + 1, ssl->heap, DYNAMIC_TYPE_DOMAIN);
7432
7433
0
    if (ssl->buffers.domainName.buffer) {
7434
0
        unsigned char* domainName = ssl->buffers.domainName.buffer;
7435
0
        XMEMCPY(domainName, dn, ssl->buffers.domainName.length);
7436
0
        domainName[ssl->buffers.domainName.length] = '\0';
7437
0
        return WOLFSSL_SUCCESS;
7438
0
    }
7439
0
    else {
7440
0
        ssl->error = MEMORY_ERROR;
7441
0
        return WOLFSSL_FAILURE;
7442
0
    }
7443
0
}
7444
7445
#if defined(SESSION_CERTS) && defined(OPENSSL_EXTRA)
7446
const char *wolfSSL_get0_peername(WOLFSSL *ssl) {
7447
    if (ssl == NULL) {
7448
        return NULL;
7449
    }
7450
7451
    if (ssl->buffers.domainName.buffer)
7452
        return (const char *)ssl->buffers.domainName.buffer;
7453
    else if (ssl->session && ssl->session->peer)
7454
        return ssl->session->peer->subjectCN;
7455
#ifdef KEEP_PEER_CERT
7456
    else if (ssl->peerCert.subjectCN[0])
7457
        return ssl->peerCert.subjectCN;
7458
#endif
7459
    else {
7460
        ssl->error = NO_PEER_CERT;
7461
        return NULL;
7462
    }
7463
}
7464
7465
#endif /* SESSION_CERTS && OPENSSL_EXTRA */
7466
7467
/* turn on wolfSSL zlib compression
7468
   returns WOLFSSL_SUCCESS for success, else error (not built in)
7469
*/
7470
int wolfSSL_set_compression(WOLFSSL* ssl)
7471
0
{
7472
0
    WOLFSSL_ENTER("wolfSSL_set_compression");
7473
0
    (void)ssl;
7474
#ifdef HAVE_LIBZ
7475
    ssl->options.usingCompression = 1;
7476
    return WOLFSSL_SUCCESS;
7477
#else
7478
0
    return NOT_COMPILED_IN;
7479
0
#endif
7480
0
}
7481
7482
7483
#ifndef USE_WINDOWS_API
7484
    #if !defined(NO_WRITEV) && !defined(NO_TLS)
7485
7486
        /* simulate writev semantics, doesn't actually do block at a time though
7487
           because of SSL_write behavior and because front adds may be small */
7488
        int wolfSSL_writev(WOLFSSL* ssl, const struct iovec* iov, int iovcnt)
7489
0
        {
7490
0
        #ifdef WOLFSSL_SMALL_STACK
7491
0
            byte   staticBuffer[1]; /* force heap usage */
7492
        #else
7493
            byte   staticBuffer[FILE_BUFFER_SIZE];
7494
        #endif
7495
0
            byte* myBuffer  = staticBuffer;
7496
0
            int   dynamic   = 0;
7497
0
            size_t sending   = 0;
7498
0
            size_t idx       = 0;
7499
0
            int   i;
7500
0
            int   ret;
7501
7502
0
            WOLFSSL_ENTER("wolfSSL_writev");
7503
7504
0
            for (i = 0; i < iovcnt; i++)
7505
0
                if (! WC_SAFE_SUM_UNSIGNED(size_t, sending, iov[i].iov_len,
7506
0
                                           sending))
7507
0
                    return BUFFER_E;
7508
7509
0
            if (sending > sizeof(staticBuffer)) {
7510
0
                myBuffer = (byte*)XMALLOC(sending, ssl->heap,
7511
0
                                          DYNAMIC_TYPE_WRITEV);
7512
0
                if (!myBuffer)
7513
0
                    return MEMORY_ERROR;
7514
7515
0
                dynamic = 1;
7516
0
            }
7517
7518
0
            for (i = 0; i < iovcnt; i++) {
7519
0
                XMEMCPY(&myBuffer[idx], iov[i].iov_base, iov[i].iov_len);
7520
0
                idx += (int)iov[i].iov_len;
7521
0
            }
7522
7523
           /* myBuffer may not be initialized fully, but the span up to the
7524
            * sending length will be.
7525
            */
7526
0
            PRAGMA_GCC_DIAG_PUSH
7527
0
            PRAGMA_GCC("GCC diagnostic ignored \"-Wmaybe-uninitialized\"")
7528
0
            ret = wolfSSL_write_internal(ssl, myBuffer, sending);
7529
0
            PRAGMA_GCC_DIAG_POP
7530
7531
0
            if (dynamic)
7532
0
                XFREE(myBuffer, ssl->heap, DYNAMIC_TYPE_WRITEV);
7533
7534
0
            return ret;
7535
0
        }
7536
    #endif
7537
#endif
7538
7539
7540
#ifdef WOLFSSL_CALLBACKS
7541
7542
    typedef struct itimerval Itimerval;
7543
7544
    /* don't keep calling simple functions while setting up timer and signals
7545
       if no inlining these are the next best */
7546
7547
    #define AddTimes(a, b, c)                       \
7548
        do {                                        \
7549
            (c).tv_sec  = (a).tv_sec + (b).tv_sec;  \
7550
            (c).tv_usec = (a).tv_usec + (b).tv_usec;\
7551
            if ((c).tv_usec >=  1000000) {          \
7552
                (c).tv_sec++;                       \
7553
                (c).tv_usec -= 1000000;             \
7554
            }                                       \
7555
        } while (0)
7556
7557
7558
    #define SubtractTimes(a, b, c)                  \
7559
        do {                                        \
7560
            (c).tv_sec  = (a).tv_sec - (b).tv_sec;  \
7561
            (c).tv_usec = (a).tv_usec - (b).tv_usec;\
7562
            if ((c).tv_usec < 0) {                  \
7563
                (c).tv_sec--;                       \
7564
                (c).tv_usec += 1000000;             \
7565
            }                                       \
7566
        } while (0)
7567
7568
    #define CmpTimes(a, b, cmp)                     \
7569
        (((a).tv_sec  ==  (b).tv_sec) ?             \
7570
            ((a).tv_usec cmp (b).tv_usec) :         \
7571
            ((a).tv_sec  cmp (b).tv_sec))           \
7572
7573
7574
    /* do nothing handler */
7575
    static void myHandler(int signo)
7576
    {
7577
        (void)signo;
7578
        return;
7579
    }
7580
7581
7582
    static int wolfSSL_ex_wrapper(WOLFSSL* ssl, HandShakeCallBack hsCb,
7583
                                 TimeoutCallBack toCb, WOLFSSL_TIMEVAL timeout)
7584
    {
7585
        int       ret        = WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR);
7586
        int       oldTimerOn = 0;   /* was timer already on */
7587
        WOLFSSL_TIMEVAL startTime;
7588
        WOLFSSL_TIMEVAL endTime;
7589
        WOLFSSL_TIMEVAL totalTime;
7590
        Itimerval myTimeout;
7591
        Itimerval oldTimeout; /* if old timer adjust from total time to reset */
7592
        struct sigaction act, oact;
7593
7594
        #define ERR_OUT(x) { ssl->hsInfoOn = 0; ssl->toInfoOn = 0; return x; }
7595
7596
        if (hsCb) {
7597
            ssl->hsInfoOn = 1;
7598
            InitHandShakeInfo(&ssl->handShakeInfo, ssl);
7599
        }
7600
        if (toCb) {
7601
            ssl->toInfoOn = 1;
7602
            InitTimeoutInfo(&ssl->timeoutInfo);
7603
7604
            if (gettimeofday(&startTime, 0) < 0)
7605
                ERR_OUT(GETTIME_ERROR);
7606
7607
            /* use setitimer to simulate getitimer, init 0 myTimeout */
7608
            myTimeout.it_interval.tv_sec  = 0;
7609
            myTimeout.it_interval.tv_usec = 0;
7610
            myTimeout.it_value.tv_sec     = 0;
7611
            myTimeout.it_value.tv_usec    = 0;
7612
            if (setitimer(ITIMER_REAL, &myTimeout, &oldTimeout) < 0)
7613
                ERR_OUT(SETITIMER_ERROR);
7614
7615
            if (oldTimeout.it_value.tv_sec || oldTimeout.it_value.tv_usec) {
7616
                oldTimerOn = 1;
7617
7618
                /* is old timer going to expire before ours */
7619
                if (CmpTimes(oldTimeout.it_value, timeout, <)) {
7620
                    timeout.tv_sec  = oldTimeout.it_value.tv_sec;
7621
                    timeout.tv_usec = oldTimeout.it_value.tv_usec;
7622
                }
7623
            }
7624
            myTimeout.it_value.tv_sec  = timeout.tv_sec;
7625
            myTimeout.it_value.tv_usec = timeout.tv_usec;
7626
7627
            /* set up signal handler, don't restart socket send/recv */
7628
            act.sa_handler = myHandler;
7629
            sigemptyset(&act.sa_mask);
7630
            act.sa_flags = 0;
7631
#ifdef SA_INTERRUPT
7632
            act.sa_flags |= SA_INTERRUPT;
7633
#endif
7634
            if (sigaction(SIGALRM, &act, &oact) < 0)
7635
                ERR_OUT(SIGACT_ERROR);
7636
7637
            if (setitimer(ITIMER_REAL, &myTimeout, 0) < 0)
7638
                ERR_OUT(SETITIMER_ERROR);
7639
        }
7640
7641
        /* do main work */
7642
#ifndef NO_WOLFSSL_CLIENT
7643
        if (ssl->options.side == WOLFSSL_CLIENT_END)
7644
            ret = wolfSSL_connect(ssl);
7645
#endif
7646
#ifndef NO_WOLFSSL_SERVER
7647
        if (ssl->options.side == WOLFSSL_SERVER_END)
7648
            ret = wolfSSL_accept(ssl);
7649
#endif
7650
7651
        /* do callbacks */
7652
        if (toCb) {
7653
            if (oldTimerOn) {
7654
                if (gettimeofday(&endTime, 0) < 0)
7655
                    ERR_OUT(SYSLIB_FAILED_E);
7656
                SubtractTimes(endTime, startTime, totalTime);
7657
                /* adjust old timer for elapsed time */
7658
                if (CmpTimes(totalTime, oldTimeout.it_value, <))
7659
                    SubtractTimes(oldTimeout.it_value, totalTime,
7660
                                  oldTimeout.it_value);
7661
                else {
7662
                    /* reset value to interval, may be off */
7663
                    oldTimeout.it_value.tv_sec = oldTimeout.it_interval.tv_sec;
7664
                    oldTimeout.it_value.tv_usec =oldTimeout.it_interval.tv_usec;
7665
                }
7666
                /* keep iter the same whether there or not */
7667
            }
7668
            /* restore old handler */
7669
            if (sigaction(SIGALRM, &oact, 0) < 0)
7670
                ret = SIGACT_ERROR;    /* more pressing error, stomp */
7671
            else
7672
                /* use old settings which may turn off (expired or not there) */
7673
                if (setitimer(ITIMER_REAL, &oldTimeout, 0) < 0)
7674
                    ret = SETITIMER_ERROR;
7675
7676
            /* if we had a timeout call callback */
7677
            if (ssl->timeoutInfo.timeoutName[0]) {
7678
                ssl->timeoutInfo.timeoutValue.tv_sec  = timeout.tv_sec;
7679
                ssl->timeoutInfo.timeoutValue.tv_usec = timeout.tv_usec;
7680
                (toCb)(&ssl->timeoutInfo);
7681
            }
7682
            ssl->toInfoOn = 0;
7683
        }
7684
7685
        /* clean up buffers allocated by AddPacketInfo */
7686
        FreeTimeoutInfo(&ssl->timeoutInfo, ssl->heap);
7687
7688
        if (hsCb) {
7689
            FinishHandShakeInfo(&ssl->handShakeInfo);
7690
            (hsCb)(&ssl->handShakeInfo);
7691
            ssl->hsInfoOn = 0;
7692
        }
7693
        return ret;
7694
    }
7695
7696
7697
#ifndef NO_WOLFSSL_CLIENT
7698
7699
    int wolfSSL_connect_ex(WOLFSSL* ssl, HandShakeCallBack hsCb,
7700
                          TimeoutCallBack toCb, WOLFSSL_TIMEVAL timeout)
7701
    {
7702
        WOLFSSL_ENTER("wolfSSL_connect_ex");
7703
        return wolfSSL_ex_wrapper(ssl, hsCb, toCb, timeout);
7704
    }
7705
7706
#endif
7707
7708
7709
#ifndef NO_WOLFSSL_SERVER
7710
7711
    int wolfSSL_accept_ex(WOLFSSL* ssl, HandShakeCallBack hsCb,
7712
                         TimeoutCallBack toCb, WOLFSSL_TIMEVAL timeout)
7713
    {
7714
        WOLFSSL_ENTER("wolfSSL_accept_ex");
7715
        return wolfSSL_ex_wrapper(ssl, hsCb, toCb, timeout);
7716
    }
7717
7718
#endif
7719
7720
#endif /* WOLFSSL_CALLBACKS */
7721
7722
7723
#ifndef NO_PSK
7724
7725
    void wolfSSL_CTX_set_psk_client_callback(WOLFSSL_CTX* ctx,
7726
                                         wc_psk_client_callback cb)
7727
    {
7728
        WOLFSSL_ENTER("wolfSSL_CTX_set_psk_client_callback");
7729
7730
        if (ctx == NULL)
7731
            return;
7732
7733
        ctx->havePSK = 1;
7734
        ctx->client_psk_cb = cb;
7735
    }
7736
7737
    void wolfSSL_set_psk_client_callback(WOLFSSL* ssl,wc_psk_client_callback cb)
7738
    {
7739
        byte haveRSA = 1;
7740
        int  keySz   = 0;
7741
7742
        WOLFSSL_ENTER("wolfSSL_set_psk_client_callback");
7743
7744
        if (ssl == NULL)
7745
            return;
7746
7747
        ssl->options.havePSK = 1;
7748
        ssl->options.client_psk_cb = cb;
7749
7750
        #ifdef NO_RSA
7751
            haveRSA = 0;
7752
        #endif
7753
        #ifndef NO_CERTS
7754
            keySz = ssl->buffers.keySz;
7755
        #endif
7756
        if (AllocateSuites(ssl) != 0)
7757
            return;
7758
        InitSuites(ssl->suites, ssl->version, keySz, haveRSA, TRUE,
7759
                   ssl->options.haveDH, ssl->options.haveECDSAsig,
7760
                   ssl->options.haveECC, TRUE, ssl->options.haveStaticECC,
7761
                   ssl->options.useAnon, TRUE, TRUE, TRUE, TRUE, ssl->options.side);
7762
    }
7763
    #ifdef OPENSSL_EXTRA
7764
    /**
7765
     * set call back function for psk session use
7766
     * @param ssl  a pointer to WOLFSSL structure
7767
     * @param cb   a function pointer to wc_psk_use_session_cb
7768
     * @return none
7769
     */
7770
    void wolfSSL_set_psk_use_session_callback(WOLFSSL* ssl,
7771
                                                wc_psk_use_session_cb_func cb)
7772
    {
7773
        WOLFSSL_ENTER("wolfSSL_set_psk_use_session_callback");
7774
7775
        if (ssl != NULL) {
7776
            ssl->options.havePSK = 1;
7777
            ssl->options.session_psk_cb = cb;
7778
        }
7779
7780
        WOLFSSL_LEAVE("wolfSSL_set_psk_use_session_callback", WOLFSSL_SUCCESS);
7781
    }
7782
    #endif
7783
7784
    void wolfSSL_CTX_set_psk_server_callback(WOLFSSL_CTX* ctx,
7785
                                         wc_psk_server_callback cb)
7786
    {
7787
        WOLFSSL_ENTER("wolfSSL_CTX_set_psk_server_callback");
7788
        if (ctx == NULL)
7789
            return;
7790
        ctx->havePSK = 1;
7791
        ctx->server_psk_cb = cb;
7792
    }
7793
7794
    void wolfSSL_set_psk_server_callback(WOLFSSL* ssl,wc_psk_server_callback cb)
7795
    {
7796
        byte haveRSA = 1;
7797
        int  keySz   = 0;
7798
7799
        WOLFSSL_ENTER("wolfSSL_set_psk_server_callback");
7800
        if (ssl == NULL)
7801
            return;
7802
7803
        ssl->options.havePSK = 1;
7804
        ssl->options.server_psk_cb = cb;
7805
7806
        #ifdef NO_RSA
7807
            haveRSA = 0;
7808
        #endif
7809
        #ifndef NO_CERTS
7810
            keySz = ssl->buffers.keySz;
7811
        #endif
7812
        if (AllocateSuites(ssl) != 0)
7813
            return;
7814
        InitSuites(ssl->suites, ssl->version, keySz, haveRSA, TRUE,
7815
                   ssl->options.haveDH, ssl->options.haveECDSAsig,
7816
                   ssl->options.haveECC, TRUE, ssl->options.haveStaticECC,
7817
                   ssl->options.useAnon, TRUE, TRUE, TRUE, TRUE, ssl->options.side);
7818
    }
7819
7820
    const char* wolfSSL_get_psk_identity_hint(const WOLFSSL* ssl)
7821
    {
7822
        WOLFSSL_ENTER("wolfSSL_get_psk_identity_hint");
7823
7824
        if (ssl == NULL || ssl->arrays == NULL)
7825
            return NULL;
7826
7827
        return ssl->arrays->server_hint;
7828
    }
7829
7830
7831
    const char* wolfSSL_get_psk_identity(const WOLFSSL* ssl)
7832
    {
7833
        WOLFSSL_ENTER("wolfSSL_get_psk_identity");
7834
7835
        if (ssl == NULL || ssl->arrays == NULL)
7836
            return NULL;
7837
7838
        return ssl->arrays->client_identity;
7839
    }
7840
7841
    int wolfSSL_CTX_use_psk_identity_hint(WOLFSSL_CTX* ctx, const char* hint)
7842
    {
7843
        WOLFSSL_ENTER("wolfSSL_CTX_use_psk_identity_hint");
7844
        if (hint == 0)
7845
            ctx->server_hint[0] = '\0';
7846
        else {
7847
            /* Qt does not call CTX_set_*_psk_callbacks where havePSK is set */
7848
            #ifdef WOLFSSL_QT
7849
            ctx->havePSK=1;
7850
            #endif
7851
            XSTRNCPY(ctx->server_hint, hint, MAX_PSK_ID_LEN);
7852
            ctx->server_hint[MAX_PSK_ID_LEN] = '\0'; /* null term */
7853
        }
7854
        return WOLFSSL_SUCCESS;
7855
    }
7856
7857
    int wolfSSL_use_psk_identity_hint(WOLFSSL* ssl, const char* hint)
7858
    {
7859
        WOLFSSL_ENTER("wolfSSL_use_psk_identity_hint");
7860
7861
        if (ssl == NULL || ssl->arrays == NULL)
7862
            return WOLFSSL_FAILURE;
7863
7864
        if (hint == 0)
7865
            ssl->arrays->server_hint[0] = 0;
7866
        else {
7867
            XSTRNCPY(ssl->arrays->server_hint, hint,
7868
                                            sizeof(ssl->arrays->server_hint)-1);
7869
            ssl->arrays->server_hint[sizeof(ssl->arrays->server_hint)-1] = '\0';
7870
        }
7871
        return WOLFSSL_SUCCESS;
7872
    }
7873
7874
    void* wolfSSL_get_psk_callback_ctx(WOLFSSL* ssl)
7875
    {
7876
        return ssl ? ssl->options.psk_ctx : NULL;
7877
    }
7878
    void* wolfSSL_CTX_get_psk_callback_ctx(WOLFSSL_CTX* ctx)
7879
    {
7880
        return ctx ? ctx->psk_ctx : NULL;
7881
    }
7882
    int wolfSSL_set_psk_callback_ctx(WOLFSSL* ssl, void* psk_ctx)
7883
    {
7884
        if (ssl == NULL)
7885
            return WOLFSSL_FAILURE;
7886
        ssl->options.psk_ctx = psk_ctx;
7887
        return WOLFSSL_SUCCESS;
7888
    }
7889
    int wolfSSL_CTX_set_psk_callback_ctx(WOLFSSL_CTX* ctx, void* psk_ctx)
7890
    {
7891
        if (ctx == NULL)
7892
            return WOLFSSL_FAILURE;
7893
        ctx->psk_ctx = psk_ctx;
7894
        return WOLFSSL_SUCCESS;
7895
    }
7896
#endif /* NO_PSK */
7897
7898
7899
#ifdef HAVE_ANON
7900
7901
    int wolfSSL_CTX_allow_anon_cipher(WOLFSSL_CTX* ctx)
7902
    {
7903
        WOLFSSL_ENTER("wolfSSL_CTX_allow_anon_cipher");
7904
7905
        if (ctx == NULL)
7906
            return WOLFSSL_FAILURE;
7907
7908
        ctx->useAnon = 1;
7909
7910
        return WOLFSSL_SUCCESS;
7911
    }
7912
7913
#endif /* HAVE_ANON */
7914
7915
#ifdef OPENSSL_EXTRA
7916
7917
    int wolfSSL_add_all_algorithms(void)
7918
0
    {
7919
0
        WOLFSSL_ENTER("wolfSSL_add_all_algorithms");
7920
0
        if (initRefCount != 0 || wolfSSL_Init() == WOLFSSL_SUCCESS)
7921
0
            return WOLFSSL_SUCCESS;
7922
0
        else
7923
0
            return WOLFSSL_FATAL_ERROR;
7924
0
    }
7925
7926
    int wolfSSL_OpenSSL_add_all_algorithms_noconf(void)
7927
0
    {
7928
0
        WOLFSSL_ENTER("wolfSSL_OpenSSL_add_all_algorithms_noconf");
7929
7930
0
        if  (wolfSSL_add_all_algorithms() ==
7931
0
             WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR))
7932
0
        {
7933
0
            return WOLFSSL_FATAL_ERROR;
7934
0
        }
7935
7936
0
        return  WOLFSSL_SUCCESS;
7937
0
    }
7938
7939
    int wolfSSL_OpenSSL_add_all_algorithms_conf(void)
7940
0
    {
7941
0
        WOLFSSL_ENTER("wolfSSL_OpenSSL_add_all_algorithms_conf");
7942
        /* This function is currently the same as
7943
        wolfSSL_OpenSSL_add_all_algorithms_noconf since we do not employ
7944
        the use of a wolfssl.cnf type configuration file and is only used for
7945
        OpenSSL compatibility. */
7946
7947
0
        if (wolfSSL_add_all_algorithms() ==
7948
0
            WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR))
7949
0
        {
7950
0
            return WOLFSSL_FATAL_ERROR;
7951
0
        }
7952
0
        return WOLFSSL_SUCCESS;
7953
0
    }
7954
7955
#endif
7956
7957
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL) || \
7958
    defined(WOLFSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
7959
    void wolfSSL_CTX_set_quiet_shutdown(WOLFSSL_CTX* ctx, int mode)
7960
0
    {
7961
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_quiet_shutdown");
7962
0
        if (mode)
7963
0
            ctx->quietShutdown = 1;
7964
0
    }
7965
7966
7967
    void wolfSSL_set_quiet_shutdown(WOLFSSL* ssl, int mode)
7968
0
    {
7969
0
        WOLFSSL_ENTER("wolfSSL_set_quiet_shutdown");
7970
0
        if (mode)
7971
0
            ssl->options.quietShutdown = 1;
7972
0
    }
7973
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL ||
7974
          WOLFSSL_EXTRA || WOLFSSL_WPAS_SMALL */
7975
7976
#ifdef OPENSSL_EXTRA
7977
#ifndef NO_BIO
7978
    static void ssl_set_bio(WOLFSSL* ssl, WOLFSSL_BIO* rd, WOLFSSL_BIO* wr, int flags)
7979
0
    {
7980
0
        WOLFSSL_ENTER("wolfSSL_set_bio");
7981
7982
0
        if (ssl == NULL) {
7983
0
            WOLFSSL_MSG("Bad argument, ssl was NULL");
7984
0
            return;
7985
0
        }
7986
7987
        /* free any existing WOLFSSL_BIOs in use but don't free those in
7988
         * a chain */
7989
0
        if ((flags & WOLFSSL_BIO_FLAG_READ) && (ssl->biord != NULL)) {
7990
0
            if ((flags & WOLFSSL_BIO_FLAG_WRITE) && (ssl->biord != ssl->biowr)) {
7991
0
                if (ssl->biowr != NULL && ssl->biowr->prev != NULL)
7992
0
                    wolfSSL_BIO_free(ssl->biowr);
7993
0
                ssl->biowr = NULL;
7994
0
            }
7995
0
            if (ssl->biord->prev != NULL)
7996
0
                wolfSSL_BIO_free(ssl->biord);
7997
0
            ssl->biord = NULL;
7998
0
        }
7999
0
        else if ((flags & WOLFSSL_BIO_FLAG_WRITE) && (ssl->biowr != NULL)) {
8000
0
            if (ssl->biowr->prev != NULL)
8001
0
                wolfSSL_BIO_free(ssl->biowr);
8002
0
            ssl->biowr = NULL;
8003
0
        }
8004
8005
        /* set flag obviously */
8006
0
        if (rd && !(rd->flags & WOLFSSL_BIO_FLAG_READ))
8007
0
            rd->flags |= WOLFSSL_BIO_FLAG_READ;
8008
0
        if (wr && !(wr->flags & WOLFSSL_BIO_FLAG_WRITE))
8009
0
            wr->flags |= WOLFSSL_BIO_FLAG_WRITE;
8010
8011
0
        if (flags & WOLFSSL_BIO_FLAG_READ)
8012
0
            ssl->biord = rd;
8013
0
        if (flags & WOLFSSL_BIO_FLAG_WRITE)
8014
0
            ssl->biowr = wr;
8015
8016
        /* set SSL to use BIO callbacks instead */
8017
0
        if ((flags & WOLFSSL_BIO_FLAG_READ) &&
8018
0
            (((ssl->cbioFlag & WOLFSSL_CBIO_RECV) == 0)))
8019
0
        {
8020
0
            ssl->CBIORecv = SslBioReceive;
8021
0
        }
8022
0
        if ((flags & WOLFSSL_BIO_FLAG_WRITE) &&
8023
0
            (((ssl->cbioFlag & WOLFSSL_CBIO_SEND) == 0)))
8024
0
        {
8025
0
            ssl->CBIOSend = SslBioSend;
8026
0
        }
8027
8028
        /* User programs should always retry reading from these BIOs */
8029
0
        if (rd) {
8030
            /* User writes to rd */
8031
0
            wolfSSL_BIO_set_retry_write(rd);
8032
0
        }
8033
0
        if (wr) {
8034
            /* User reads from wr */
8035
0
            wolfSSL_BIO_set_retry_read(wr);
8036
0
        }
8037
0
    }
8038
8039
    void wolfSSL_set_bio(WOLFSSL* ssl, WOLFSSL_BIO* rd, WOLFSSL_BIO* wr)
8040
0
    {
8041
0
        ssl_set_bio(ssl, rd, wr, WOLFSSL_BIO_FLAG_READ | WOLFSSL_BIO_FLAG_WRITE);
8042
0
    }
8043
8044
    void wolfSSL_set_rbio(WOLFSSL* ssl, WOLFSSL_BIO* rd)
8045
0
    {
8046
0
        ssl_set_bio(ssl, rd, NULL, WOLFSSL_BIO_FLAG_READ);
8047
0
    }
8048
8049
    void wolfSSL_set_wbio(WOLFSSL* ssl, WOLFSSL_BIO* wr)
8050
0
    {
8051
0
        ssl_set_bio(ssl, NULL, wr, WOLFSSL_BIO_FLAG_WRITE);
8052
0
    }
8053
8054
#endif /* !NO_BIO */
8055
#endif /* OPENSSL_EXTRA */
8056
8057
#ifdef WOLFSSL_CERT_SETUP_CB
8058
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
8059
    /* registers client cert callback, called during handshake if server
8060
       requests client auth but user has not loaded client cert/key */
8061
    void wolfSSL_CTX_set_client_cert_cb(WOLFSSL_CTX *ctx, client_cert_cb cb)
8062
0
    {
8063
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_client_cert_cb");
8064
8065
0
        if (ctx != NULL) {
8066
0
            ctx->CBClientCert = cb;
8067
0
        }
8068
0
    }
8069
#endif
8070
8071
    void wolfSSL_CTX_set_cert_cb(WOLFSSL_CTX* ctx,
8072
        CertSetupCallback cb, void *arg)
8073
0
    {
8074
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_cert_cb");
8075
0
        if (ctx == NULL)
8076
0
            return;
8077
8078
0
        ctx->certSetupCb = cb;
8079
0
        ctx->certSetupCbArg = arg;
8080
0
    }
8081
8082
    int wolfSSL_get_client_suites_sigalgs(const WOLFSSL* ssl,
8083
            const byte** suites, word16* suiteSz,
8084
            const byte** hashSigAlgo, word16* hashSigAlgoSz)
8085
0
    {
8086
0
        WOLFSSL_ENTER("wolfSSL_get_client_suites_sigalgs");
8087
8088
0
        if (suites != NULL)
8089
0
            *suites = NULL;
8090
0
        if (suiteSz != NULL)
8091
0
            *suiteSz = 0;
8092
0
        if (hashSigAlgo != NULL)
8093
0
            *hashSigAlgo = NULL;
8094
0
        if (hashSigAlgoSz != NULL)
8095
0
            *hashSigAlgoSz = 0;
8096
8097
0
        if (ssl != NULL && ssl->clSuites != NULL) {
8098
0
            if (suites != NULL && suiteSz != NULL) {
8099
0
                *suites = ssl->clSuites->suites;
8100
0
                *suiteSz = ssl->clSuites->suiteSz;
8101
0
            }
8102
0
            if (hashSigAlgo != NULL && hashSigAlgoSz != NULL) {
8103
0
                *hashSigAlgo = ssl->clSuites->hashSigAlgo;
8104
0
                *hashSigAlgoSz = ssl->clSuites->hashSigAlgoSz;
8105
0
            }
8106
0
            return WOLFSSL_SUCCESS;
8107
0
        }
8108
0
        return WOLFSSL_FAILURE;
8109
0
    }
8110
8111
#ifndef NO_TLS
8112
    WOLFSSL_CIPHERSUITE_INFO wolfSSL_get_ciphersuite_info(byte first,
8113
            byte second)
8114
0
    {
8115
0
        WOLFSSL_CIPHERSUITE_INFO info;
8116
0
        info.rsaAuth = (byte)(CipherRequires(first, second, REQUIRES_RSA) ||
8117
0
                CipherRequires(first, second, REQUIRES_RSA_SIG));
8118
0
        info.eccAuth = (byte)(CipherRequires(first, second, REQUIRES_ECC) ||
8119
                /* Static ECC ciphers may require RSA for authentication */
8120
0
                (CipherRequires(first, second, REQUIRES_ECC_STATIC) &&
8121
0
                        !CipherRequires(first, second, REQUIRES_RSA_SIG)));
8122
0
        info.eccStatic =
8123
0
                (byte)CipherRequires(first, second, REQUIRES_ECC_STATIC);
8124
0
        info.psk = (byte)CipherRequires(first, second, REQUIRES_PSK);
8125
0
        return info;
8126
0
    }
8127
#endif
8128
8129
    /**
8130
     * @param first First byte of the hash and signature algorithm
8131
     * @param second Second byte of the hash and signature algorithm
8132
     * @param hashAlgo The enum wc_HashType of the MAC algorithm
8133
     * @param sigAlgo The enum Key_Sum of the authentication algorithm
8134
     */
8135
    int wolfSSL_get_sigalg_info(byte first, byte second,
8136
            int* hashAlgo, int* sigAlgo)
8137
0
    {
8138
0
        byte input[2];
8139
0
        byte hashType;
8140
0
        byte sigType;
8141
8142
0
        if (hashAlgo == NULL || sigAlgo == NULL)
8143
0
            return BAD_FUNC_ARG;
8144
8145
0
        input[0] = first;
8146
0
        input[1] = second;
8147
0
        DecodeSigAlg(input, &hashType, &sigType);
8148
8149
        /* cast so that compiler reminds us of unimplemented values */
8150
0
        switch ((enum SignatureAlgorithm)sigType) {
8151
0
        case anonymous_sa_algo:
8152
0
            *sigAlgo = ANONk;
8153
0
            break;
8154
0
        case rsa_sa_algo:
8155
0
            *sigAlgo = RSAk;
8156
0
            break;
8157
0
        case dsa_sa_algo:
8158
0
            *sigAlgo = DSAk;
8159
0
            break;
8160
0
        case ecc_dsa_sa_algo:
8161
0
        case ecc_brainpool_sa_algo:
8162
0
            *sigAlgo = ECDSAk;
8163
0
            break;
8164
0
        case rsa_pss_sa_algo:
8165
0
            *sigAlgo = RSAPSSk;
8166
0
            break;
8167
0
        case ed25519_sa_algo:
8168
0
            *sigAlgo = ED25519k;
8169
0
            break;
8170
0
        case rsa_pss_pss_algo:
8171
0
            *sigAlgo = RSAPSSk;
8172
0
            break;
8173
0
        case ed448_sa_algo:
8174
0
            *sigAlgo = ED448k;
8175
0
            break;
8176
0
        case falcon_level1_sa_algo:
8177
0
            *sigAlgo = FALCON_LEVEL1k;
8178
0
            break;
8179
0
        case falcon_level5_sa_algo:
8180
0
            *sigAlgo = FALCON_LEVEL5k;
8181
0
            break;
8182
0
        case dilithium_level2_sa_algo:
8183
0
            *sigAlgo = ML_DSA_LEVEL2k;
8184
0
            break;
8185
0
        case dilithium_level3_sa_algo:
8186
0
            *sigAlgo = ML_DSA_LEVEL3k;
8187
0
            break;
8188
0
        case dilithium_level5_sa_algo:
8189
0
            *sigAlgo = ML_DSA_LEVEL5k;
8190
0
            break;
8191
0
        case sm2_sa_algo:
8192
0
            *sigAlgo = SM2k;
8193
0
            break;
8194
0
        case invalid_sa_algo:
8195
0
        case any_sa_algo:
8196
0
        default:
8197
0
            *hashAlgo = WC_HASH_TYPE_NONE;
8198
0
            *sigAlgo = 0;
8199
0
            return BAD_FUNC_ARG;
8200
0
        }
8201
8202
        /* cast so that compiler reminds us of unimplemented values */
8203
0
        switch((enum wc_MACAlgorithm)hashType) {
8204
0
        case no_mac:
8205
0
        case rmd_mac: /* Don't have a RIPEMD type in wc_HashType */
8206
0
            *hashAlgo = WC_HASH_TYPE_NONE;
8207
0
            break;
8208
0
        case md5_mac:
8209
0
            *hashAlgo = WC_HASH_TYPE_MD5;
8210
0
            break;
8211
0
        case sha_mac:
8212
0
            *hashAlgo = WC_HASH_TYPE_SHA;
8213
0
            break;
8214
0
        case sha224_mac:
8215
0
            *hashAlgo = WC_HASH_TYPE_SHA224;
8216
0
            break;
8217
0
        case sha256_mac:
8218
0
            *hashAlgo = WC_HASH_TYPE_SHA256;
8219
0
            break;
8220
0
        case sha384_mac:
8221
0
            *hashAlgo = WC_HASH_TYPE_SHA384;
8222
0
            break;
8223
0
        case sha512_mac:
8224
0
            *hashAlgo = WC_HASH_TYPE_SHA512;
8225
0
            break;
8226
0
        case blake2b_mac:
8227
0
            *hashAlgo = WC_HASH_TYPE_BLAKE2B;
8228
0
            break;
8229
0
        case sm3_mac:
8230
0
#ifdef WOLFSSL_SM3
8231
0
            *hashAlgo = WC_HASH_TYPE_SM3;
8232
#else
8233
            *hashAlgo = WC_HASH_TYPE_NONE;
8234
#endif
8235
0
            break;
8236
0
        default:
8237
0
            *hashAlgo = WC_HASH_TYPE_NONE;
8238
0
            *sigAlgo = 0;
8239
0
            return BAD_FUNC_ARG;
8240
0
        }
8241
0
        return 0;
8242
0
    }
8243
8244
    /**
8245
     * Internal wrapper for calling certSetupCb
8246
     * @param ssl The SSL/TLS Object
8247
     * @return 0 on success
8248
     */
8249
    int CertSetupCbWrapper(WOLFSSL* ssl)
8250
1.27k
    {
8251
1.27k
        int ret = 0;
8252
1.27k
        if (ssl->ctx->certSetupCb != NULL) {
8253
0
            WOLFSSL_MSG("Calling user cert setup callback");
8254
0
            ret = ssl->ctx->certSetupCb(ssl, ssl->ctx->certSetupCbArg);
8255
0
            if (ret == 1) {
8256
0
                WOLFSSL_MSG("User cert callback returned success");
8257
0
                ret = 0;
8258
0
            }
8259
0
            else if (ret == 0) {
8260
0
                SendAlert(ssl, alert_fatal, internal_error);
8261
0
                ret = CLIENT_CERT_CB_ERROR;
8262
0
            }
8263
0
            else if (ret < 0) {
8264
0
                ret = WOLFSSL_ERROR_WANT_X509_LOOKUP;
8265
0
            }
8266
0
            else {
8267
0
                WOLFSSL_MSG("Unexpected user callback return");
8268
0
                ret = CLIENT_CERT_CB_ERROR;
8269
0
            }
8270
0
        }
8271
1.27k
        return ret;
8272
1.27k
    }
8273
#endif /* WOLFSSL_CERT_SETUP_CB */
8274
8275
#ifdef OPENSSL_EXTRA
8276
8277
    #if defined(WOLFCRYPT_HAVE_SRP) && !defined(NO_SHA256) \
8278
        && !defined(WC_NO_RNG)
8279
    static const byte srp_N[] = {
8280
        0xEE, 0xAF, 0x0A, 0xB9, 0xAD, 0xB3, 0x8D, 0xD6, 0x9C, 0x33, 0xF8,
8281
        0x0A, 0xFA, 0x8F, 0xC5, 0xE8, 0x60, 0x72, 0x61, 0x87, 0x75, 0xFF,
8282
        0x3C, 0x0B, 0x9E, 0xA2, 0x31, 0x4C, 0x9C, 0x25, 0x65, 0x76, 0xD6,
8283
        0x74, 0xDF, 0x74, 0x96, 0xEA, 0x81, 0xD3, 0x38, 0x3B, 0x48, 0x13,
8284
        0xD6, 0x92, 0xC6, 0xE0, 0xE0, 0xD5, 0xD8, 0xE2, 0x50, 0xB9, 0x8B,
8285
        0xE4, 0x8E, 0x49, 0x5C, 0x1D, 0x60, 0x89, 0xDA, 0xD1, 0x5D, 0xC7,
8286
        0xD7, 0xB4, 0x61, 0x54, 0xD6, 0xB6, 0xCE, 0x8E, 0xF4, 0xAD, 0x69,
8287
        0xB1, 0x5D, 0x49, 0x82, 0x55, 0x9B, 0x29, 0x7B, 0xCF, 0x18, 0x85,
8288
        0xC5, 0x29, 0xF5, 0x66, 0x66, 0x0E, 0x57, 0xEC, 0x68, 0xED, 0xBC,
8289
        0x3C, 0x05, 0x72, 0x6C, 0xC0, 0x2F, 0xD4, 0xCB, 0xF4, 0x97, 0x6E,
8290
        0xAA, 0x9A, 0xFD, 0x51, 0x38, 0xFE, 0x83, 0x76, 0x43, 0x5B, 0x9F,
8291
        0xC6, 0x1D, 0x2F, 0xC0, 0xEB, 0x06, 0xE3
8292
    };
8293
    static const byte srp_g[] = {
8294
        0x02
8295
    };
8296
8297
    int wolfSSL_CTX_set_srp_username(WOLFSSL_CTX* ctx, char* username)
8298
    {
8299
        int r = 0;
8300
        SrpSide srp_side = SRP_CLIENT_SIDE;
8301
8302
        WOLFSSL_ENTER("wolfSSL_CTX_set_srp_username");
8303
        if (ctx == NULL || ctx->srp == NULL || username==NULL)
8304
            return WOLFSSL_FAILURE;
8305
8306
        if (ctx->method->side == WOLFSSL_SERVER_END){
8307
            srp_side = SRP_SERVER_SIDE;
8308
        } else if (ctx->method->side == WOLFSSL_CLIENT_END){
8309
            srp_side = SRP_CLIENT_SIDE;
8310
        } else {
8311
            WOLFSSL_MSG("Init CTX failed");
8312
            return WOLFSSL_FAILURE;
8313
        }
8314
8315
        if (wc_SrpInit(ctx->srp, SRP_TYPE_SHA256, srp_side) < 0) {
8316
            WOLFSSL_MSG("Init SRP CTX failed");
8317
            XFREE(ctx->srp, ctx->heap, DYNAMIC_TYPE_SRP);
8318
            ctx->srp = NULL;
8319
            return WOLFSSL_FAILURE;
8320
        }
8321
        r = wc_SrpSetUsername(ctx->srp, (const byte*)username,
8322
                              (word32)XSTRLEN(username));
8323
        if (r < 0) {
8324
            WOLFSSL_MSG("fail to set srp username.");
8325
            return WOLFSSL_FAILURE;
8326
        }
8327
8328
        /* if wolfSSL_CTX_set_srp_password has already been called, */
8329
        /* use saved password here */
8330
        if (ctx->srp_password != NULL) {
8331
            if (ctx->srp->user == NULL)
8332
                return WOLFSSL_FAILURE;
8333
            return wolfSSL_CTX_set_srp_password(ctx, (char*)ctx->srp_password);
8334
        }
8335
8336
        return WOLFSSL_SUCCESS;
8337
    }
8338
8339
    int wolfSSL_CTX_set_srp_password(WOLFSSL_CTX* ctx, char* password)
8340
    {
8341
        int r;
8342
        byte salt[SRP_SALT_SIZE];
8343
8344
        WOLFSSL_ENTER("wolfSSL_CTX_set_srp_password");
8345
        if (ctx == NULL || ctx->srp == NULL || password == NULL)
8346
            return WOLFSSL_FAILURE;
8347
8348
        if (ctx->srp->user != NULL) {
8349
            WC_RNG rng;
8350
            if (wc_InitRng(&rng) < 0) {
8351
                WOLFSSL_MSG("wc_InitRng failed");
8352
                return WOLFSSL_FAILURE;
8353
            }
8354
            XMEMSET(salt, 0, sizeof(salt)/sizeof(salt[0]));
8355
            r = wc_RNG_GenerateBlock(&rng, salt, sizeof(salt)/sizeof(salt[0]));
8356
            wc_FreeRng(&rng);
8357
            if (r <  0) {
8358
                WOLFSSL_MSG("wc_RNG_GenerateBlock failed");
8359
                return WOLFSSL_FAILURE;
8360
            }
8361
            if (wc_SrpSetParams(ctx->srp, srp_N, sizeof(srp_N)/sizeof(srp_N[0]),
8362
                                srp_g, sizeof(srp_g)/sizeof(srp_g[0]),
8363
                                salt, sizeof(salt)/sizeof(salt[0])) < 0){
8364
                WOLFSSL_MSG("wc_SrpSetParam failed");
8365
                return WOLFSSL_FAILURE;
8366
            }
8367
            r = wc_SrpSetPassword(ctx->srp, (const byte*)password,
8368
                                  (word32)XSTRLEN(password));
8369
            if (r < 0) {
8370
                WOLFSSL_MSG("wc_SrpSetPassword failed.");
8371
                return WOLFSSL_FAILURE;
8372
            }
8373
            XFREE(ctx->srp_password, NULL, DYNAMIC_TYPE_SRP);
8374
            ctx->srp_password = NULL;
8375
        } else {
8376
            /* save password for wolfSSL_set_srp_username */
8377
            XFREE(ctx->srp_password, ctx->heap, DYNAMIC_TYPE_SRP);
8378
8379
            ctx->srp_password = (byte*)XMALLOC(XSTRLEN(password) + 1, ctx->heap,
8380
                                               DYNAMIC_TYPE_SRP);
8381
            if (ctx->srp_password == NULL){
8382
                WOLFSSL_MSG("memory allocation error");
8383
                return WOLFSSL_FAILURE;
8384
            }
8385
            XMEMCPY(ctx->srp_password, password, XSTRLEN(password) + 1);
8386
        }
8387
        return WOLFSSL_SUCCESS;
8388
    }
8389
8390
    /**
8391
     * The modulus passed to wc_SrpSetParams in ssl.c is constant so check
8392
     * that the requested strength is less than or equal to the size of the
8393
     * static modulus size.
8394
     * @param ctx Not used
8395
     * @param strength Minimum number of bits for the modulus
8396
     * @return 1 if strength is less than or equal to static modulus
8397
     *         0 if strength is greater than static modulus
8398
     */
8399
    int  wolfSSL_CTX_set_srp_strength(WOLFSSL_CTX *ctx, int strength)
8400
    {
8401
        (void)ctx;
8402
        WOLFSSL_ENTER("wolfSSL_CTX_set_srp_strength");
8403
        if (strength > (int)(sizeof(srp_N)*8)) {
8404
            WOLFSSL_MSG("Bad Parameter");
8405
            return WOLFSSL_FAILURE;
8406
        }
8407
        return WOLFSSL_SUCCESS;
8408
    }
8409
8410
    char* wolfSSL_get_srp_username(WOLFSSL *ssl)
8411
    {
8412
        if (ssl && ssl->ctx && ssl->ctx->srp) {
8413
            return (char*) ssl->ctx->srp->user;
8414
        }
8415
        return NULL;
8416
    }
8417
    #endif /* WOLFCRYPT_HAVE_SRP && !NO_SHA256 && !WC_NO_RNG */
8418
8419
    /* keyblock size in bytes or -1 */
8420
    int wolfSSL_get_keyblock_size(WOLFSSL* ssl)
8421
0
    {
8422
0
        if (ssl == NULL)
8423
0
            return WOLFSSL_FATAL_ERROR;
8424
8425
0
        return 2 * (ssl->specs.key_size + ssl->specs.iv_size +
8426
0
                    ssl->specs.hash_size);
8427
0
    }
8428
8429
#endif /* OPENSSL_EXTRA */
8430
8431
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_EXTRA) || \
8432
    defined(WOLFSSL_WPAS_SMALL)
8433
8434
    /* store keys returns WOLFSSL_SUCCESS or -1 on error */
8435
    int wolfSSL_get_keys(WOLFSSL* ssl, unsigned char** ms, unsigned int* msLen,
8436
                                     unsigned char** sr, unsigned int* srLen,
8437
                                     unsigned char** cr, unsigned int* crLen)
8438
0
    {
8439
0
        if (ssl == NULL || ssl->arrays == NULL)
8440
0
            return WOLFSSL_FATAL_ERROR;
8441
8442
0
        *ms = ssl->arrays->masterSecret;
8443
0
        *sr = ssl->arrays->serverRandom;
8444
0
        *cr = ssl->arrays->clientRandom;
8445
8446
0
        *msLen = SECRET_LEN;
8447
0
        *srLen = RAN_LEN;
8448
0
        *crLen = RAN_LEN;
8449
8450
0
        return WOLFSSL_SUCCESS;
8451
0
    }
8452
8453
    void wolfSSL_set_accept_state(WOLFSSL* ssl)
8454
0
    {
8455
0
        WOLFSSL_ENTER("wolfSSL_set_accept_state");
8456
8457
0
        if (ssl == NULL)
8458
0
            return;
8459
8460
0
        if (ssl->options.side == WOLFSSL_CLIENT_END) {
8461
0
    #ifdef HAVE_ECC
8462
0
            WC_DECLARE_VAR(key, ecc_key, 1, 0);
8463
0
            word32 idx = 0;
8464
8465
0
        #ifdef WOLFSSL_SMALL_STACK
8466
0
            key = (ecc_key*)XMALLOC(sizeof(ecc_key), ssl->heap,
8467
0
                                    DYNAMIC_TYPE_ECC);
8468
0
            if (key == NULL) {
8469
0
                WOLFSSL_MSG("Error allocating memory for ecc_key");
8470
0
            }
8471
0
        #endif
8472
0
            if (ssl->options.haveStaticECC && ssl->buffers.key != NULL) {
8473
0
                if (wc_ecc_init(key) >= 0) {
8474
0
                    if (wc_EccPrivateKeyDecode(ssl->buffers.key->buffer, &idx,
8475
0
                            key, ssl->buffers.key->length) != 0) {
8476
0
                        ssl->options.haveECDSAsig = 0;
8477
0
                        ssl->options.haveECC = 0;
8478
0
                        ssl->options.haveStaticECC = 0;
8479
0
                    }
8480
0
                    wc_ecc_free(key);
8481
0
                }
8482
0
            }
8483
0
            WC_FREE_VAR_EX(key, ssl->heap, DYNAMIC_TYPE_ECC);
8484
0
    #endif
8485
8486
0
    #ifndef NO_DH
8487
0
            if (!ssl->options.haveDH && ssl->ctx->haveDH) {
8488
0
                ssl->buffers.serverDH_P = ssl->ctx->serverDH_P;
8489
0
                ssl->buffers.serverDH_G = ssl->ctx->serverDH_G;
8490
0
                ssl->options.haveDH = 1;
8491
0
            }
8492
0
    #endif
8493
0
        }
8494
8495
0
        if (InitSSL_Side(ssl, WOLFSSL_SERVER_END) != WOLFSSL_SUCCESS) {
8496
0
            WOLFSSL_MSG("Error initializing server side");
8497
0
        }
8498
0
    }
8499
8500
#endif /* OPENSSL_EXTRA || WOLFSSL_EXTRA || WOLFSSL_WPAS_SMALL */
8501
8502
    /* return true if connection established */
8503
    /* this works for TLS and DTLS */
8504
    int wolfSSL_is_init_finished(const WOLFSSL* ssl)
8505
0
    {
8506
0
        if (ssl == NULL)
8507
0
            return 0;
8508
8509
#if defined(WOLFSSL_DTLS13) && !defined(WOLFSSL_NO_CLIENT)
8510
        if (ssl->options.side == WOLFSSL_CLIENT_END && ssl->options.dtls
8511
                && IsAtLeastTLSv1_3(ssl->version)) {
8512
            return ssl->options.serverState == SERVER_FINISHED_ACKED;
8513
        }
8514
#endif /* WOLFSSL_DTLS13 && !WOLFSSL_NO_CLIENT */
8515
8516
        /* Can't use ssl->options.connectState and ssl->options.acceptState
8517
         * because they differ in meaning for TLS <=1.2 and 1.3 */
8518
0
        if (ssl->options.handShakeState == HANDSHAKE_DONE)
8519
0
            return 1;
8520
8521
0
        return 0;
8522
0
    }
8523
8524
#ifdef OPENSSL_EXTRA
8525
    void wolfSSL_CTX_set_tmp_rsa_callback(WOLFSSL_CTX* ctx,
8526
                                      WOLFSSL_RSA*(*f)(WOLFSSL*, int, int))
8527
0
    {
8528
        /* wolfSSL verifies all these internally */
8529
0
        (void)ctx;
8530
0
        (void)f;
8531
0
    }
8532
8533
8534
    void wolfSSL_set_shutdown(WOLFSSL* ssl, int opt)
8535
0
    {
8536
0
        WOLFSSL_ENTER("wolfSSL_set_shutdown");
8537
0
        if(ssl==NULL) {
8538
0
            WOLFSSL_MSG("Shutdown not set. ssl is null");
8539
0
            return;
8540
0
        }
8541
8542
0
        ssl->options.sentNotify =  (opt&WOLFSSL_SENT_SHUTDOWN) > 0;
8543
0
        ssl->options.closeNotify = (opt&WOLFSSL_RECEIVED_SHUTDOWN) > 0;
8544
0
    }
8545
#endif
8546
8547
    long wolfSSL_CTX_get_options(WOLFSSL_CTX* ctx)
8548
0
    {
8549
0
        WOLFSSL_ENTER("wolfSSL_CTX_get_options");
8550
0
        WOLFSSL_MSG("wolfSSL options are set through API calls and macros");
8551
0
        if(ctx == NULL)
8552
0
            return BAD_FUNC_ARG;
8553
0
        return (long)ctx->mask;
8554
0
    }
8555
8556
    /* forward declaration */
8557
    static long wolf_set_options(long old_op, long op);
8558
8559
    long wolfSSL_CTX_set_options(WOLFSSL_CTX* ctx, long opt)
8560
0
    {
8561
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_options");
8562
8563
0
        if (ctx == NULL)
8564
0
            return BAD_FUNC_ARG;
8565
8566
0
        ctx->mask = (unsigned long)wolf_set_options((long)ctx->mask, opt);
8567
0
#if defined(HAVE_SESSION_TICKET) && (defined(OPENSSL_EXTRA) \
8568
0
        || defined(HAVE_WEBSERVER) || defined(WOLFSSL_WPAS_SMALL))
8569
0
        if ((ctx->mask & WOLFSSL_OP_NO_TICKET) == WOLFSSL_OP_NO_TICKET) {
8570
0
          ctx->noTicketTls12 = 1;
8571
0
        }
8572
        /* This code is here for documentation purpose. You must not turn off
8573
         * session tickets with the WOLFSSL_OP_NO_TICKET option for TLSv1.3.
8574
         * Because we need to support both stateful and stateless tickets.
8575
        #ifdef WOLFSSL_TLS13
8576
            if ((ctx->mask & WOLFSSL_OP_NO_TICKET) == WOLFSSL_OP_NO_TICKET) {
8577
                ctx->noTicketTls13 = 1;
8578
            }
8579
        #endif
8580
        */
8581
0
#endif
8582
0
        return (long)ctx->mask;
8583
0
    }
8584
8585
    long wolfSSL_CTX_clear_options(WOLFSSL_CTX* ctx, long opt)
8586
0
    {
8587
0
        WOLFSSL_ENTER("wolfSSL_CTX_clear_options");
8588
0
        if(ctx == NULL)
8589
0
            return BAD_FUNC_ARG;
8590
0
        ctx->mask &= (unsigned long)~opt;
8591
0
        return (long)ctx->mask;
8592
0
    }
8593
8594
#ifdef OPENSSL_EXTRA
8595
8596
    int wolfSSL_set_rfd(WOLFSSL* ssl, int rfd)
8597
0
    {
8598
0
        WOLFSSL_ENTER("wolfSSL_set_rfd");
8599
0
        ssl->rfd = rfd;      /* not used directly to allow IO callbacks */
8600
8601
0
        ssl->IOCB_ReadCtx  = &ssl->rfd;
8602
8603
    #ifdef WOLFSSL_DTLS
8604
        if (ssl->options.dtls) {
8605
            ssl->IOCB_ReadCtx = &ssl->buffers.dtlsCtx;
8606
            ssl->buffers.dtlsCtx.rfd = rfd;
8607
        }
8608
    #endif
8609
8610
0
        return WOLFSSL_SUCCESS;
8611
0
    }
8612
8613
8614
    int wolfSSL_set_wfd(WOLFSSL* ssl, int wfd)
8615
0
    {
8616
0
        WOLFSSL_ENTER("wolfSSL_set_wfd");
8617
0
        ssl->wfd = wfd;      /* not used directly to allow IO callbacks */
8618
8619
0
        ssl->IOCB_WriteCtx  = &ssl->wfd;
8620
8621
0
        return WOLFSSL_SUCCESS;
8622
0
    }
8623
#endif /* OPENSSL_EXTRA */
8624
8625
#ifdef WOLFSSL_ENCRYPTED_KEYS
8626
8627
    void wolfSSL_CTX_set_default_passwd_cb_userdata(WOLFSSL_CTX* ctx,
8628
                                                   void* userdata)
8629
0
    {
8630
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_default_passwd_cb_userdata");
8631
0
        if (ctx)
8632
0
            ctx->passwd_userdata = userdata;
8633
0
    }
8634
8635
8636
    void wolfSSL_CTX_set_default_passwd_cb(WOLFSSL_CTX* ctx, wc_pem_password_cb*
8637
                                           cb)
8638
0
    {
8639
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_default_passwd_cb");
8640
0
        if (ctx)
8641
0
            ctx->passwd_cb = cb;
8642
0
    }
8643
8644
    wc_pem_password_cb* wolfSSL_CTX_get_default_passwd_cb(WOLFSSL_CTX *ctx)
8645
0
    {
8646
0
        if (ctx == NULL || ctx->passwd_cb == NULL) {
8647
0
            return NULL;
8648
0
        }
8649
8650
0
        return ctx->passwd_cb;
8651
0
    }
8652
8653
8654
    void* wolfSSL_CTX_get_default_passwd_cb_userdata(WOLFSSL_CTX *ctx)
8655
0
    {
8656
0
        if (ctx == NULL) {
8657
0
            return NULL;
8658
0
        }
8659
8660
0
        return ctx->passwd_userdata;
8661
0
    }
8662
8663
#endif /* WOLFSSL_ENCRYPTED_KEYS */
8664
8665
8666
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER) || defined(HAVE_MEMCACHED)
8667
    unsigned long wolfSSL_ERR_get_error(void)
8668
0
    {
8669
0
        WOLFSSL_ENTER("wolfSSL_ERR_get_error");
8670
0
#ifdef WOLFSSL_HAVE_ERROR_QUEUE
8671
0
        return (unsigned long)wc_GetErrorNodeErr();
8672
#else
8673
        return (unsigned long)(0 - NOT_COMPILED_IN);
8674
#endif
8675
0
    }
8676
#endif
8677
8678
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
8679
8680
    int wolfSSL_num_locks(void)
8681
0
    {
8682
0
        return 0;
8683
0
    }
8684
8685
    void wolfSSL_set_locking_callback(mutex_cb* f)
8686
0
    {
8687
0
        WOLFSSL_ENTER("wolfSSL_set_locking_callback");
8688
8689
0
        if (wc_SetMutexCb(f) != 0) {
8690
0
            WOLFSSL_MSG("Error when setting mutex call back");
8691
0
        }
8692
0
    }
8693
8694
    mutex_cb* wolfSSL_get_locking_callback(void)
8695
0
    {
8696
0
        WOLFSSL_ENTER("wolfSSL_get_locking_callback");
8697
8698
0
        return wc_GetMutexCb();
8699
0
    }
8700
8701
8702
    typedef unsigned long (idCb)(void);
8703
    static idCb* inner_idCb = NULL;
8704
8705
    unsigned long wolfSSL_thread_id(void)
8706
0
    {
8707
0
        if (inner_idCb != NULL) {
8708
0
            return inner_idCb();
8709
0
        }
8710
0
        else {
8711
0
            return 0;
8712
0
        }
8713
0
    }
8714
8715
8716
    void wolfSSL_set_id_callback(unsigned long (*f)(void))
8717
0
    {
8718
0
        inner_idCb = f;
8719
0
    }
8720
8721
#ifdef WOLFSSL_HAVE_ERROR_QUEUE
8722
#ifndef NO_BIO
8723
    /* print out and clear all errors */
8724
    void wolfSSL_ERR_print_errors(WOLFSSL_BIO* bio)
8725
0
    {
8726
0
        const char* file = NULL;
8727
0
        const char* reason = NULL;
8728
0
        int ret;
8729
0
        int line = 0;
8730
0
        char buf[WOLFSSL_MAX_ERROR_SZ * 2];
8731
8732
0
        WOLFSSL_ENTER("wolfSSL_ERR_print_errors");
8733
8734
0
        if (bio == NULL) {
8735
0
            WOLFSSL_MSG("BIO passed in was null");
8736
0
            return;
8737
0
        }
8738
8739
0
        do {
8740
0
        ret = wc_PeekErrorNode(0, &file, &reason, &line);
8741
0
        if (ret >= 0) {
8742
0
            const char* r = wolfSSL_ERR_reason_error_string(
8743
0
                (unsigned long)(0 - ret));
8744
0
            if (XSNPRINTF(buf, sizeof(buf),
8745
0
                          "error:%d:wolfSSL library:%s:%s:%d\n",
8746
0
                          ret, r, file, line)
8747
0
                >= (int)sizeof(buf))
8748
0
            {
8749
0
                WOLFSSL_MSG("Buffer overrun formatting error message");
8750
0
            }
8751
0
            wolfSSL_BIO_write(bio, buf, (int)XSTRLEN(buf));
8752
0
            wc_RemoveErrorNode(0);
8753
0
        }
8754
0
        } while (ret >= 0);
8755
0
        if (wolfSSL_BIO_write(bio, "", 1) != 1) {
8756
0
            WOLFSSL_MSG("Issue writing final string terminator");
8757
0
        }
8758
0
    }
8759
#endif /* !NO_BIO */
8760
#endif /* WOLFSSL_HAVE_ERROR_QUEUE */
8761
8762
#endif /* OPENSSL_EXTRA || HAVE_WEBSERVER */
8763
8764
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL) || \
8765
    defined(HAVE_SECRET_CALLBACK)
8766
#if !defined(NO_WOLFSSL_SERVER)
8767
/* Return the amount of random bytes copied over or error case.
8768
 * ssl : ssl struct after handshake
8769
 * out : buffer to hold random bytes
8770
 * outSz : either 0 (return max buffer sz) or size of out buffer
8771
 */
8772
size_t wolfSSL_get_server_random(const WOLFSSL *ssl, unsigned char *out,
8773
                                                                   size_t outSz)
8774
0
{
8775
0
    size_t size;
8776
8777
    /* return max size of buffer */
8778
0
    if (outSz == 0) {
8779
0
        return RAN_LEN;
8780
0
    }
8781
8782
0
    if (ssl == NULL || out == NULL) {
8783
0
        return 0;
8784
0
    }
8785
8786
0
    if (ssl->arrays == NULL) {
8787
0
        WOLFSSL_MSG("Arrays struct not saved after handshake");
8788
0
        return 0;
8789
0
    }
8790
8791
0
    if (outSz > RAN_LEN) {
8792
0
        size = RAN_LEN;
8793
0
    }
8794
0
    else {
8795
0
        size = outSz;
8796
0
    }
8797
8798
0
    XMEMCPY(out, ssl->arrays->serverRandom, size);
8799
0
    return size;
8800
0
}
8801
#endif /* !NO_WOLFSSL_SERVER */
8802
#endif /* OPENSSL_EXTRA || WOLFSSL_WPAS_SMALL || HAVE_SECRET_CALLBACK */
8803
8804
#ifdef OPENSSL_EXTRA
8805
#if !defined(NO_WOLFSSL_SERVER)
8806
/* Used to get the peer ephemeral public key sent during the connection
8807
 * NOTE: currently wolfSSL_KeepHandshakeResources(WOLFSSL* ssl) must be called
8808
 *       before the ephemeral key is stored.
8809
 * return WOLFSSL_SUCCESS on success */
8810
int wolfSSL_get_peer_tmp_key(const WOLFSSL* ssl, WOLFSSL_EVP_PKEY** pkey)
8811
0
{
8812
0
    WOLFSSL_EVP_PKEY* ret = NULL;
8813
8814
0
    WOLFSSL_ENTER("wolfSSL_get_server_tmp_key");
8815
8816
0
    if (ssl == NULL || pkey == NULL) {
8817
0
        WOLFSSL_MSG("Bad argument passed in");
8818
0
        return WOLFSSL_FAILURE;
8819
0
    }
8820
8821
0
#ifdef HAVE_ECC
8822
0
    if (ssl->peerEccKey != NULL) {
8823
0
        unsigned char* der;
8824
0
        const unsigned char* pt;
8825
0
        unsigned int   derSz = 0;
8826
0
        int sz;
8827
8828
0
        PRIVATE_KEY_UNLOCK();
8829
0
        if (wc_ecc_export_x963(ssl->peerEccKey, NULL, &derSz)
8830
0
              != WC_NO_ERR_TRACE(LENGTH_ONLY_E))
8831
0
        {
8832
0
            WOLFSSL_MSG("get ecc der size failed");
8833
0
            PRIVATE_KEY_LOCK();
8834
0
            return WOLFSSL_FAILURE;
8835
0
        }
8836
0
        PRIVATE_KEY_LOCK();
8837
8838
0
        derSz += MAX_SEQ_SZ + (2 * MAX_ALGO_SZ) + MAX_SEQ_SZ + TRAILING_ZERO;
8839
0
        der = (unsigned char*)XMALLOC(derSz, ssl->heap, DYNAMIC_TYPE_KEY);
8840
0
        if (der == NULL) {
8841
0
            WOLFSSL_MSG("Memory error");
8842
0
            return WOLFSSL_FAILURE;
8843
0
        }
8844
8845
0
        if ((sz = wc_EccPublicKeyToDer(ssl->peerEccKey, der, derSz, 1)) <= 0) {
8846
0
            WOLFSSL_MSG("get ecc der failed");
8847
0
            XFREE(der, ssl->heap, DYNAMIC_TYPE_KEY);
8848
0
            return WOLFSSL_FAILURE;
8849
0
        }
8850
0
        pt = der; /* in case pointer gets advanced */
8851
0
        ret = wolfSSL_d2i_PUBKEY(NULL, &pt, sz);
8852
0
        XFREE(der, ssl->heap, DYNAMIC_TYPE_KEY);
8853
0
    }
8854
0
#endif
8855
8856
0
    *pkey = ret;
8857
0
#ifdef HAVE_ECC
8858
0
    if (ret != NULL)
8859
0
        return WOLFSSL_SUCCESS;
8860
0
    else
8861
0
#endif
8862
0
        return WOLFSSL_FAILURE;
8863
0
}
8864
8865
#endif /* !NO_WOLFSSL_SERVER */
8866
8867
/**
8868
 * This function checks if any compiled in protocol versions are
8869
 * left enabled after calls to set_min or set_max API.
8870
 * @param major The SSL/TLS major version
8871
 * @return WOLFSSL_SUCCESS on valid settings and WOLFSSL_FAILURE when no
8872
 *         protocol versions are left enabled.
8873
 */
8874
static int CheckSslMethodVersion(byte major, unsigned long options)
8875
0
{
8876
0
    int sanityConfirmed = 0;
8877
8878
0
    (void)options;
8879
8880
0
    switch (major) {
8881
0
    #ifndef NO_TLS
8882
0
        case SSLv3_MAJOR:
8883
            #ifdef WOLFSSL_ALLOW_SSLV3
8884
                if (!(options & WOLFSSL_OP_NO_SSLv3)) {
8885
                    sanityConfirmed = 1;
8886
                }
8887
            #endif
8888
            #ifndef NO_OLD_TLS
8889
                if (!(options & WOLFSSL_OP_NO_TLSv1))
8890
                    sanityConfirmed = 1;
8891
                if (!(options & WOLFSSL_OP_NO_TLSv1_1))
8892
                    sanityConfirmed = 1;
8893
            #endif
8894
0
            #ifndef WOLFSSL_NO_TLS12
8895
0
                if (!(options & WOLFSSL_OP_NO_TLSv1_2))
8896
0
                    sanityConfirmed = 1;
8897
0
            #endif
8898
0
            #ifdef WOLFSSL_TLS13
8899
0
                if (!(options & WOLFSSL_OP_NO_TLSv1_3))
8900
0
                    sanityConfirmed = 1;
8901
0
            #endif
8902
0
            break;
8903
0
    #endif
8904
    #ifdef WOLFSSL_DTLS
8905
        case DTLS_MAJOR:
8906
            sanityConfirmed = 1;
8907
            break;
8908
    #endif
8909
0
        default:
8910
0
            WOLFSSL_MSG("Invalid major version");
8911
0
            return WOLFSSL_FAILURE;
8912
0
    }
8913
0
    if (!sanityConfirmed) {
8914
0
        WOLFSSL_MSG("All compiled in TLS versions disabled");
8915
0
        return WOLFSSL_FAILURE;
8916
0
    }
8917
0
    return WOLFSSL_SUCCESS;
8918
0
}
8919
8920
/**
8921
 * protoVerTbl holds (D)TLS version numbers in ascending order.
8922
 * Except DTLS versions, the newer version is located in the latter part of
8923
 * the table. This table is referred by wolfSSL_CTX_set_min_proto_version and
8924
 * wolfSSL_CTX_set_max_proto_version.
8925
 */
8926
static const int protoVerTbl[] = {
8927
    SSL3_VERSION,
8928
    TLS1_VERSION,
8929
    TLS1_1_VERSION,
8930
    TLS1_2_VERSION,
8931
    TLS1_3_VERSION,
8932
    DTLS1_VERSION,
8933
    DTLS1_2_VERSION
8934
};
8935
/* number of protocol versions listed in protoVerTbl */
8936
0
#define NUMBER_OF_PROTOCOLS (sizeof(protoVerTbl)/sizeof(int))
8937
8938
/**
8939
 * wolfSSL_CTX_set_min_proto_version attempts to set the minimum protocol
8940
 * version to use by SSL objects created from this WOLFSSL_CTX.
8941
 * This API guarantees that a version of SSL/TLS lower than specified
8942
 * here will not be allowed. If the version specified is not compiled in
8943
 * then this API sets the lowest compiled in protocol version.
8944
 * This API also accept 0 as version, to set the minimum version automatically.
8945
 * CheckSslMethodVersion() is called to check if any remaining protocol versions
8946
 * are enabled.
8947
 * @param ctx The wolfSSL CONTEXT factory for spawning SSL/TLS objects
8948
 * @param version Any of the following
8949
 *          * 0
8950
 *          * SSL3_VERSION
8951
 *          * TLS1_VERSION
8952
 *          * TLS1_1_VERSION
8953
 *          * TLS1_2_VERSION
8954
 *          * TLS1_3_VERSION
8955
 *          * DTLS1_VERSION
8956
 *          * DTLS1_2_VERSION
8957
 * @return WOLFSSL_SUCCESS on valid settings and WOLFSSL_FAILURE when no
8958
 *         protocol versions are left enabled.
8959
 */
8960
static int Set_CTX_min_proto_version(WOLFSSL_CTX* ctx, int version)
8961
0
{
8962
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_min_proto_version_ex");
8963
8964
0
    if (ctx == NULL) {
8965
0
        return WOLFSSL_FAILURE;
8966
0
    }
8967
8968
0
    switch (version) {
8969
0
#ifndef NO_TLS
8970
0
        case SSL3_VERSION:
8971
#if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS)
8972
            ctx->minDowngrade = SSLv3_MINOR;
8973
            break;
8974
#endif
8975
0
        case TLS1_VERSION:
8976
        #ifdef WOLFSSL_ALLOW_TLSV10
8977
            ctx->minDowngrade = TLSv1_MINOR;
8978
            break;
8979
        #endif
8980
0
        case TLS1_1_VERSION:
8981
        #ifndef NO_OLD_TLS
8982
            ctx->minDowngrade = TLSv1_1_MINOR;
8983
            break;
8984
        #endif
8985
0
        case TLS1_2_VERSION:
8986
0
        #ifndef WOLFSSL_NO_TLS12
8987
0
            ctx->minDowngrade = TLSv1_2_MINOR;
8988
0
            break;
8989
0
        #endif
8990
0
        case TLS1_3_VERSION:
8991
0
        #ifdef WOLFSSL_TLS13
8992
0
            ctx->minDowngrade = TLSv1_3_MINOR;
8993
0
            break;
8994
0
        #endif
8995
0
#endif
8996
#ifdef WOLFSSL_DTLS
8997
        case DTLS1_VERSION:
8998
    #ifndef NO_OLD_TLS
8999
            ctx->minDowngrade = DTLS_MINOR;
9000
            break;
9001
    #endif
9002
        case DTLS1_2_VERSION:
9003
            ctx->minDowngrade = DTLSv1_2_MINOR;
9004
            break;
9005
#endif
9006
0
        default:
9007
0
            WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9008
0
            return WOLFSSL_FAILURE;
9009
0
    }
9010
9011
0
    switch (version) {
9012
0
#ifndef NO_TLS
9013
0
    case TLS1_3_VERSION:
9014
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1_2);
9015
0
        FALL_THROUGH;
9016
0
    case TLS1_2_VERSION:
9017
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1_1);
9018
0
        FALL_THROUGH;
9019
0
    case TLS1_1_VERSION:
9020
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1);
9021
0
        FALL_THROUGH;
9022
0
    case TLS1_VERSION:
9023
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_SSLv3);
9024
0
        break;
9025
0
    case SSL3_VERSION:
9026
0
    case SSL2_VERSION:
9027
        /* Nothing to do here */
9028
0
        break;
9029
0
#endif
9030
#ifdef WOLFSSL_DTLS
9031
    case DTLS1_VERSION:
9032
    case DTLS1_2_VERSION:
9033
        break;
9034
#endif
9035
0
    default:
9036
0
        WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9037
0
        return WOLFSSL_FAILURE;
9038
0
    }
9039
9040
0
    return CheckSslMethodVersion(ctx->method->version.major, ctx->mask);
9041
0
}
9042
9043
/* Sets the min protocol version allowed with WOLFSSL_CTX
9044
 * returns WOLFSSL_SUCCESS on success */
9045
int wolfSSL_CTX_set_min_proto_version(WOLFSSL_CTX* ctx, int version)
9046
0
{
9047
0
    int ret;
9048
0
    int proto    = 0;
9049
0
    int maxProto = 0;
9050
0
    int i;
9051
0
    int idx = 0;
9052
9053
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_min_proto_version");
9054
9055
0
    if (ctx == NULL) {
9056
0
        return WOLFSSL_FAILURE;
9057
0
    }
9058
9059
0
    if (version != 0) {
9060
0
        proto = version;
9061
0
        ctx->minProto = 0; /* turn min proto flag off */
9062
0
        for (i = 0; (unsigned)i < NUMBER_OF_PROTOCOLS; i++) {
9063
0
            if (protoVerTbl[i] == version) {
9064
0
                break;
9065
0
            }
9066
0
        }
9067
0
    }
9068
0
    else {
9069
        /* when 0 is specified as version, try to find out the min version */
9070
0
        for (i = 0; (unsigned)i < NUMBER_OF_PROTOCOLS; i++) {
9071
0
            ret = Set_CTX_min_proto_version(ctx, protoVerTbl[i]);
9072
0
            if (ret == WOLFSSL_SUCCESS) {
9073
0
                proto = protoVerTbl[i];
9074
0
                ctx->minProto = 1; /* turn min proto flag on */
9075
0
                break;
9076
0
            }
9077
0
        }
9078
0
    }
9079
9080
    /* check case where max > min , if so then clear the NO_* options
9081
     * i is the index into the table for proto version used, see if the max
9082
     * proto version index found is smaller */
9083
0
    maxProto = wolfSSL_CTX_get_max_proto_version(ctx);
9084
0
    for (idx = 0; (unsigned)idx < NUMBER_OF_PROTOCOLS; idx++) {
9085
0
        if (protoVerTbl[idx] == maxProto) {
9086
0
            break;
9087
0
        }
9088
0
    }
9089
0
    if (idx < i) {
9090
0
        wolfSSL_CTX_clear_options(ctx, WOLFSSL_OP_NO_TLSv1 |
9091
0
                WOLFSSL_OP_NO_TLSv1_1 | WOLFSSL_OP_NO_TLSv1_2 |
9092
0
                WOLFSSL_OP_NO_TLSv1_3);
9093
0
    }
9094
9095
0
    ret = Set_CTX_min_proto_version(ctx, proto);
9096
0
    return ret;
9097
0
}
9098
9099
/**
9100
 * wolfSSL_CTX_set_max_proto_version attempts to set the maximum protocol
9101
 * version to use by SSL objects created from this WOLFSSL_CTX.
9102
 * This API guarantees that a version of SSL/TLS higher than specified
9103
 * here will not be allowed. If the version specified is not compiled in
9104
 * then this API sets the highest compiled in protocol version.
9105
 * This API also accept 0 as version, to set the maximum version automatically.
9106
 * CheckSslMethodVersion() is called to check if any remaining protocol versions
9107
 * are enabled.
9108
 * @param ctx The wolfSSL CONTEXT factory for spawning SSL/TLS objects
9109
 * @param ver Any of the following
9110
 *          * 0
9111
 *          * SSL3_VERSION
9112
 *          * TLS1_VERSION
9113
 *          * TLS1_1_VERSION
9114
 *          * TLS1_2_VERSION
9115
 *          * TLS1_3_VERSION
9116
 *          * DTLS1_VERSION
9117
 *          * DTLS1_2_VERSION
9118
 * @return WOLFSSL_SUCCESS on valid settings and WOLFSSL_FAILURE when no
9119
 *         protocol versions are left enabled.
9120
 */
9121
static int Set_CTX_max_proto_version(WOLFSSL_CTX* ctx, int ver)
9122
0
{
9123
0
    int ret;
9124
0
    WOLFSSL_ENTER("Set_CTX_max_proto_version");
9125
9126
0
    if (!ctx || !ctx->method) {
9127
0
        WOLFSSL_MSG("Bad parameter");
9128
0
        return WOLFSSL_FAILURE;
9129
0
    }
9130
9131
0
    switch (ver) {
9132
0
#ifndef NO_TLS
9133
#ifndef NO_OLD_TLS
9134
    case SSL2_VERSION:
9135
        WOLFSSL_MSG("wolfSSL does not support SSLv2");
9136
        return WOLFSSL_FAILURE;
9137
#endif
9138
0
    case SSL3_VERSION:
9139
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1);
9140
0
        FALL_THROUGH;
9141
0
    case TLS1_VERSION:
9142
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1_1);
9143
0
        FALL_THROUGH;
9144
0
    case TLS1_1_VERSION:
9145
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1_2);
9146
0
        FALL_THROUGH;
9147
0
    case TLS1_2_VERSION:
9148
0
        wolfSSL_CTX_set_options(ctx, WOLFSSL_OP_NO_TLSv1_3);
9149
0
        FALL_THROUGH;
9150
0
    case TLS1_3_VERSION:
9151
        /* Nothing to do here */
9152
0
        break;
9153
0
#endif
9154
#ifdef WOLFSSL_DTLS
9155
    case DTLS1_VERSION:
9156
    case DTLS1_2_VERSION:
9157
        break;
9158
#endif
9159
0
    default:
9160
0
        WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9161
0
        return WOLFSSL_FAILURE;
9162
0
    }
9163
9164
0
    ret = CheckSslMethodVersion(ctx->method->version.major, ctx->mask);
9165
0
    if (ret == WOLFSSL_SUCCESS) {
9166
        /* Check the major */
9167
0
        switch (ver) {
9168
0
    #ifndef NO_TLS
9169
0
        case SSL3_VERSION:
9170
0
        case TLS1_VERSION:
9171
0
        case TLS1_1_VERSION:
9172
0
        case TLS1_2_VERSION:
9173
0
        case TLS1_3_VERSION:
9174
0
            if (ctx->method->version.major != SSLv3_MAJOR) {
9175
0
                WOLFSSL_MSG("Mismatched protocol version");
9176
0
                return WOLFSSL_FAILURE;
9177
0
            }
9178
0
            break;
9179
0
    #endif
9180
    #ifdef WOLFSSL_DTLS
9181
        case DTLS1_VERSION:
9182
        case DTLS1_2_VERSION:
9183
            if (ctx->method->version.major != DTLS_MAJOR) {
9184
                WOLFSSL_MSG("Mismatched protocol version");
9185
                return WOLFSSL_FAILURE;
9186
            }
9187
            break;
9188
    #endif
9189
0
        }
9190
        /* Update the method */
9191
0
        switch (ver) {
9192
0
    #ifndef NO_TLS
9193
0
        case SSL3_VERSION:
9194
0
            ctx->method->version.minor = SSLv3_MINOR;
9195
0
            break;
9196
0
        case TLS1_VERSION:
9197
0
            ctx->method->version.minor = TLSv1_MINOR;
9198
0
            break;
9199
0
        case TLS1_1_VERSION:
9200
0
            ctx->method->version.minor = TLSv1_1_MINOR;
9201
0
            break;
9202
0
        case TLS1_2_VERSION:
9203
0
            ctx->method->version.minor = TLSv1_2_MINOR;
9204
0
            break;
9205
0
        case TLS1_3_VERSION:
9206
0
            ctx->method->version.minor = TLSv1_3_MINOR;
9207
0
            break;
9208
0
    #endif
9209
    #ifdef WOLFSSL_DTLS
9210
        case DTLS1_VERSION:
9211
            ctx->method->version.minor = DTLS_MINOR;
9212
            break;
9213
        case DTLS1_2_VERSION:
9214
            ctx->method->version.minor = DTLSv1_2_MINOR;
9215
            break;
9216
    #endif
9217
0
        default:
9218
0
            WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9219
0
            return WOLFSSL_FAILURE;
9220
0
        }
9221
0
    }
9222
0
    return ret;
9223
0
}
9224
9225
9226
/* Sets the max protocol version allowed with WOLFSSL_CTX
9227
 * returns WOLFSSL_SUCCESS on success */
9228
int wolfSSL_CTX_set_max_proto_version(WOLFSSL_CTX* ctx, int version)
9229
0
{
9230
0
    int i;
9231
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
9232
0
    int minProto;
9233
9234
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_max_proto_version");
9235
9236
0
    if (ctx == NULL) {
9237
0
        return ret;
9238
0
    }
9239
9240
    /* clear out flags and reset min protocol version */
9241
0
    minProto = wolfSSL_CTX_get_min_proto_version(ctx);
9242
0
    wolfSSL_CTX_clear_options(ctx,
9243
0
            WOLFSSL_OP_NO_TLSv1 | WOLFSSL_OP_NO_TLSv1_1 |
9244
0
            WOLFSSL_OP_NO_TLSv1_2 | WOLFSSL_OP_NO_TLSv1_3);
9245
0
    wolfSSL_CTX_set_min_proto_version(ctx, minProto);
9246
0
    if (version != 0) {
9247
0
        ctx->maxProto = 0; /* turn max proto flag off */
9248
0
        return Set_CTX_max_proto_version(ctx, version);
9249
0
    }
9250
9251
    /* when 0 is specified as version, try to find out the min version from
9252
     * the bottom to top of the protoverTbl.
9253
     */
9254
0
    for (i = NUMBER_OF_PROTOCOLS -1; i >= 0; i--) {
9255
0
        ret = Set_CTX_max_proto_version(ctx, protoVerTbl[i]);
9256
0
        if (ret == WOLFSSL_SUCCESS) {
9257
0
            ctx->maxProto = 1; /* turn max proto flag on */
9258
0
            break;
9259
0
        }
9260
0
    }
9261
9262
0
    return ret;
9263
0
}
9264
9265
9266
static int Set_SSL_min_proto_version(WOLFSSL* ssl, int ver)
9267
0
{
9268
0
    WOLFSSL_ENTER("Set_SSL_min_proto_version");
9269
9270
0
    if (ssl == NULL) {
9271
0
        return WOLFSSL_FAILURE;
9272
0
    }
9273
9274
0
    switch (ver) {
9275
0
#ifndef NO_TLS
9276
0
        case SSL3_VERSION:
9277
#if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS)
9278
            ssl->options.minDowngrade = SSLv3_MINOR;
9279
            break;
9280
#endif
9281
0
        case TLS1_VERSION:
9282
        #ifdef WOLFSSL_ALLOW_TLSV10
9283
            ssl->options.minDowngrade = TLSv1_MINOR;
9284
            break;
9285
        #endif
9286
0
        case TLS1_1_VERSION:
9287
        #ifndef NO_OLD_TLS
9288
            ssl->options.minDowngrade = TLSv1_1_MINOR;
9289
            break;
9290
        #endif
9291
0
        case TLS1_2_VERSION:
9292
0
        #ifndef WOLFSSL_NO_TLS12
9293
0
            ssl->options.minDowngrade = TLSv1_2_MINOR;
9294
0
            break;
9295
0
        #endif
9296
0
        case TLS1_3_VERSION:
9297
0
        #ifdef WOLFSSL_TLS13
9298
0
            ssl->options.minDowngrade = TLSv1_3_MINOR;
9299
0
            break;
9300
0
        #endif
9301
0
#endif
9302
#ifdef WOLFSSL_DTLS
9303
        case DTLS1_VERSION:
9304
    #ifndef NO_OLD_TLS
9305
            ssl->options.minDowngrade = DTLS_MINOR;
9306
            break;
9307
    #endif
9308
        case DTLS1_2_VERSION:
9309
            ssl->options.minDowngrade = DTLSv1_2_MINOR;
9310
            break;
9311
#endif
9312
0
        default:
9313
0
            WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9314
0
            return WOLFSSL_FAILURE;
9315
0
    }
9316
9317
0
    switch (ver) {
9318
0
#ifndef NO_TLS
9319
0
    case TLS1_3_VERSION:
9320
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1_2;
9321
0
        FALL_THROUGH;
9322
0
    case TLS1_2_VERSION:
9323
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1_1;
9324
0
        FALL_THROUGH;
9325
0
    case TLS1_1_VERSION:
9326
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1;
9327
0
        FALL_THROUGH;
9328
0
    case TLS1_VERSION:
9329
0
        ssl->options.mask |= WOLFSSL_OP_NO_SSLv3;
9330
0
        break;
9331
0
    case SSL3_VERSION:
9332
0
    case SSL2_VERSION:
9333
        /* Nothing to do here */
9334
0
        break;
9335
0
#endif
9336
#ifdef WOLFSSL_DTLS
9337
    case DTLS1_VERSION:
9338
    case DTLS1_2_VERSION:
9339
        break;
9340
#endif
9341
0
    default:
9342
0
        WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9343
0
        return WOLFSSL_FAILURE;
9344
0
    }
9345
9346
0
    return CheckSslMethodVersion(ssl->version.major, ssl->options.mask);
9347
0
}
9348
9349
int wolfSSL_set_min_proto_version(WOLFSSL* ssl, int version)
9350
0
{
9351
0
    int i;
9352
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);;
9353
9354
0
    WOLFSSL_ENTER("wolfSSL_set_min_proto_version");
9355
9356
0
    if (ssl == NULL) {
9357
0
        return WOLFSSL_FAILURE;
9358
0
    }
9359
0
    if (version != 0) {
9360
0
        return Set_SSL_min_proto_version(ssl, version);
9361
0
    }
9362
9363
    /* when 0 is specified as version, try to find out the min version */
9364
0
    for (i= 0; (unsigned)i < NUMBER_OF_PROTOCOLS; i++) {
9365
0
        ret = Set_SSL_min_proto_version(ssl, protoVerTbl[i]);
9366
0
        if (ret == WOLFSSL_SUCCESS)
9367
0
            break;
9368
0
    }
9369
9370
0
    return ret;
9371
0
}
9372
9373
static int Set_SSL_max_proto_version(WOLFSSL* ssl, int ver)
9374
0
{
9375
9376
0
    WOLFSSL_ENTER("Set_SSL_max_proto_version");
9377
9378
0
    if (!ssl) {
9379
0
        WOLFSSL_MSG("Bad parameter");
9380
0
        return WOLFSSL_FAILURE;
9381
0
    }
9382
9383
0
    switch (ver) {
9384
0
    case SSL2_VERSION:
9385
0
        WOLFSSL_MSG("wolfSSL does not support SSLv2");
9386
0
        return WOLFSSL_FAILURE;
9387
0
#ifndef NO_TLS
9388
0
    case SSL3_VERSION:
9389
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1;
9390
0
        FALL_THROUGH;
9391
0
    case TLS1_VERSION:
9392
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1_1;
9393
0
        FALL_THROUGH;
9394
0
    case TLS1_1_VERSION:
9395
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1_2;
9396
0
        FALL_THROUGH;
9397
0
    case TLS1_2_VERSION:
9398
0
        ssl->options.mask |= WOLFSSL_OP_NO_TLSv1_3;
9399
0
        FALL_THROUGH;
9400
0
    case TLS1_3_VERSION:
9401
        /* Nothing to do here */
9402
0
        break;
9403
0
#endif
9404
#ifdef WOLFSSL_DTLS
9405
    case DTLS1_VERSION:
9406
    case DTLS1_2_VERSION:
9407
        break;
9408
#endif
9409
0
    default:
9410
0
        WOLFSSL_MSG("Unrecognized protocol version or not compiled in");
9411
0
        return WOLFSSL_FAILURE;
9412
0
    }
9413
9414
0
    return CheckSslMethodVersion(ssl->version.major, ssl->options.mask);
9415
0
}
9416
9417
int wolfSSL_set_max_proto_version(WOLFSSL* ssl, int version)
9418
0
{
9419
0
    int i;
9420
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);;
9421
9422
0
    WOLFSSL_ENTER("wolfSSL_set_max_proto_version");
9423
9424
0
    if (ssl == NULL) {
9425
0
        return WOLFSSL_FAILURE;
9426
0
    }
9427
0
    if (version != 0) {
9428
0
        return Set_SSL_max_proto_version(ssl, version);
9429
0
    }
9430
9431
    /* when 0 is specified as version, try to find out the min version from
9432
     * the bottom to top of the protoverTbl.
9433
     */
9434
0
    for (i = NUMBER_OF_PROTOCOLS -1; i >= 0; i--) {
9435
0
        ret = Set_SSL_max_proto_version(ssl, protoVerTbl[i]);
9436
0
        if (ret == WOLFSSL_SUCCESS)
9437
0
            break;
9438
0
    }
9439
9440
0
    return ret;
9441
0
}
9442
9443
static int GetMinProtoVersion(int minDowngrade)
9444
0
{
9445
0
    int ret;
9446
9447
0
    switch (minDowngrade) {
9448
#ifndef NO_OLD_TLS
9449
    #ifdef WOLFSSL_ALLOW_SSLV3
9450
        case SSLv3_MINOR:
9451
            ret = SSL3_VERSION;
9452
            break;
9453
    #endif
9454
    #ifdef WOLFSSL_ALLOW_TLSV10
9455
        case TLSv1_MINOR:
9456
            ret = TLS1_VERSION;
9457
            break;
9458
    #endif
9459
        case TLSv1_1_MINOR:
9460
            ret = TLS1_1_VERSION;
9461
            break;
9462
#endif
9463
0
#ifndef WOLFSSL_NO_TLS12
9464
0
        case TLSv1_2_MINOR:
9465
0
            ret = TLS1_2_VERSION;
9466
0
            break;
9467
0
#endif
9468
0
#ifdef WOLFSSL_TLS13
9469
0
        case TLSv1_3_MINOR:
9470
0
            ret = TLS1_3_VERSION;
9471
0
            break;
9472
0
#endif
9473
0
        default:
9474
0
            ret = 0;
9475
0
            break;
9476
0
    }
9477
9478
0
    return ret;
9479
0
}
9480
9481
int wolfSSL_CTX_get_min_proto_version(WOLFSSL_CTX* ctx)
9482
0
{
9483
0
    int ret = 0;
9484
9485
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_min_proto_version");
9486
9487
0
    if (ctx != NULL) {
9488
0
        if (ctx->minProto) {
9489
0
            ret = 0;
9490
0
        }
9491
0
        else {
9492
0
            ret = GetMinProtoVersion(ctx->minDowngrade);
9493
0
        }
9494
0
    }
9495
0
    else {
9496
0
        ret = GetMinProtoVersion(WOLFSSL_MIN_DOWNGRADE);
9497
0
    }
9498
9499
0
    WOLFSSL_LEAVE("wolfSSL_CTX_get_min_proto_version", ret);
9500
9501
0
    return ret;
9502
0
}
9503
9504
9505
/* returns the maximum allowed protocol version given the 'options' used
9506
 * returns WOLFSSL_FATAL_ERROR on no match */
9507
static int GetMaxProtoVersion(long options)
9508
0
{
9509
0
#ifndef NO_TLS
9510
0
#ifdef WOLFSSL_TLS13
9511
0
    if (!(options & WOLFSSL_OP_NO_TLSv1_3))
9512
0
        return TLS1_3_VERSION;
9513
0
#endif
9514
0
#ifndef WOLFSSL_NO_TLS12
9515
0
    if (!(options & WOLFSSL_OP_NO_TLSv1_2))
9516
0
        return TLS1_2_VERSION;
9517
0
#endif
9518
#ifndef NO_OLD_TLS
9519
    if (!(options & WOLFSSL_OP_NO_TLSv1_1))
9520
        return TLS1_1_VERSION;
9521
    #ifdef WOLFSSL_ALLOW_TLSV10
9522
    if (!(options & WOLFSSL_OP_NO_TLSv1))
9523
        return TLS1_VERSION;
9524
    #endif
9525
    #ifdef WOLFSSL_ALLOW_SSLV3
9526
    if (!(options & WOLFSSL_OP_NO_SSLv3))
9527
        return SSL3_VERSION;
9528
    #endif
9529
#endif
9530
#else
9531
    (void)options;
9532
#endif /* NO_TLS */
9533
0
    return WOLFSSL_FATAL_ERROR;
9534
0
}
9535
9536
9537
/* returns the maximum protocol version for 'ctx' */
9538
int wolfSSL_CTX_get_max_proto_version(WOLFSSL_CTX* ctx)
9539
0
{
9540
0
    int ret = 0;
9541
0
    long options = 0; /* default to nothing set */
9542
9543
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_max_proto_version");
9544
9545
0
    if (ctx != NULL) {
9546
0
        options = wolfSSL_CTX_get_options(ctx);
9547
0
    }
9548
9549
0
    if ((ctx != NULL) && ctx->maxProto) {
9550
0
        ret = 0;
9551
0
    }
9552
0
    else {
9553
0
        ret = GetMaxProtoVersion(options);
9554
0
    }
9555
9556
0
    WOLFSSL_LEAVE("wolfSSL_CTX_get_max_proto_version", ret);
9557
9558
0
    if (ret == WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR)) {
9559
0
        WOLFSSL_MSG("Error getting max proto version");
9560
0
        ret = 0; /* setting ret to 0 to match compat return */
9561
0
    }
9562
0
    return ret;
9563
0
}
9564
#endif /* OPENSSL_EXTRA */
9565
9566
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL) || \
9567
    defined(HAVE_SECRET_CALLBACK)
9568
#if !defined(NO_WOLFSSL_CLIENT)
9569
/* Return the amount of random bytes copied over or error case.
9570
 * ssl : ssl struct after handshake
9571
 * out : buffer to hold random bytes
9572
 * outSz : either 0 (return max buffer sz) or size of out buffer
9573
 */
9574
size_t wolfSSL_get_client_random(const WOLFSSL* ssl, unsigned char* out,
9575
                                                                   size_t outSz)
9576
0
{
9577
0
    size_t size;
9578
9579
    /* return max size of buffer */
9580
0
    if (outSz == 0) {
9581
0
        return RAN_LEN;
9582
0
    }
9583
9584
0
    if (ssl == NULL || out == NULL) {
9585
0
        return 0;
9586
0
    }
9587
9588
0
    if (ssl->arrays == NULL) {
9589
0
        WOLFSSL_MSG("Arrays struct not saved after handshake");
9590
0
        return 0;
9591
0
    }
9592
9593
0
    if (outSz > RAN_LEN) {
9594
0
        size = RAN_LEN;
9595
0
    }
9596
0
    else {
9597
0
        size = outSz;
9598
0
    }
9599
9600
0
    XMEMCPY(out, ssl->arrays->clientRandom, size);
9601
0
    return size;
9602
0
}
9603
#endif /* !NO_WOLFSSL_CLIENT */
9604
#endif /* OPENSSL_EXTRA || WOLFSSL_WPAS_SMALL || HAVE_SECRET_CALLBACK */
9605
9606
#ifdef OPENSSL_EXTRA
9607
9608
    unsigned long wolfSSLeay(void)
9609
0
    {
9610
0
#ifdef SSLEAY_VERSION_NUMBER
9611
0
        return SSLEAY_VERSION_NUMBER;
9612
#else
9613
        return OPENSSL_VERSION_NUMBER;
9614
#endif
9615
0
    }
9616
9617
    unsigned long wolfSSL_OpenSSL_version_num(void)
9618
0
    {
9619
0
        return OPENSSL_VERSION_NUMBER;
9620
0
    }
9621
9622
    const char* wolfSSLeay_version(int type)
9623
0
    {
9624
0
        (void)type;
9625
#if defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x10100000L
9626
        return wolfSSL_OpenSSL_version(type);
9627
#else
9628
0
        return wolfSSL_OpenSSL_version();
9629
0
#endif
9630
0
    }
9631
#endif /* OPENSSL_EXTRA */
9632
9633
#ifdef OPENSSL_EXTRA
9634
    void wolfSSL_ERR_free_strings(void)
9635
0
    {
9636
        /* handled internally */
9637
0
    }
9638
9639
    void wolfSSL_cleanup_all_ex_data(void)
9640
0
    {
9641
        /* nothing to do here */
9642
0
    }
9643
9644
#endif /* OPENSSL_EXTRA */
9645
9646
#if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) || \
9647
    defined(HAVE_CURL)
9648
    void wolfSSL_ERR_clear_error(void)
9649
0
    {
9650
0
        WOLFSSL_ENTER("wolfSSL_ERR_clear_error");
9651
0
    #if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE)
9652
0
        wc_ClearErrorNodes();
9653
0
    #endif
9654
0
    }
9655
#endif
9656
9657
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
9658
    int wolfSSL_clear(WOLFSSL* ssl)
9659
0
    {
9660
0
        WOLFSSL_ENTER("wolfSSL_clear");
9661
9662
0
        if (ssl == NULL) {
9663
0
            return WOLFSSL_FAILURE;
9664
0
        }
9665
9666
0
        if (!ssl->options.handShakeDone) {
9667
            /* Only reset the session if we didn't complete a handshake */
9668
0
            wolfSSL_FreeSession(ssl->ctx, ssl->session);
9669
0
            ssl->session = wolfSSL_NewSession(ssl->heap);
9670
0
            if (ssl->session == NULL) {
9671
0
                return WOLFSSL_FAILURE;
9672
0
            }
9673
0
        }
9674
9675
        /* reset error */
9676
0
        ssl->error = 0;
9677
9678
        /* reset option bits */
9679
0
        ssl->options.isClosed = 0;
9680
0
        ssl->options.connReset = 0;
9681
0
        ssl->options.sentNotify = 0;
9682
0
        ssl->options.closeNotify = 0;
9683
0
        ssl->options.sendVerify = 0;
9684
0
        ssl->options.serverState = NULL_STATE;
9685
0
        ssl->options.clientState = NULL_STATE;
9686
0
        ssl->options.connectState = CONNECT_BEGIN;
9687
0
        ssl->options.acceptState  = ACCEPT_BEGIN;
9688
0
        ssl->options.handShakeState  = NULL_STATE;
9689
0
        ssl->options.handShakeDone = 0;
9690
0
        ssl->options.processReply = 0; /* doProcessInit */
9691
0
        ssl->options.havePeerVerify = 0;
9692
0
        ssl->options.havePeerCert = 0;
9693
0
        ssl->options.peerAuthGood = 0;
9694
0
        ssl->options.tls1_3 = 0;
9695
0
        ssl->options.haveSessionId = 0;
9696
0
        ssl->options.tls = 0;
9697
0
        ssl->options.tls1_1 = 0;
9698
0
    #ifdef WOLFSSL_TLS13
9699
    #ifdef WOLFSSL_SEND_HRR_COOKIE
9700
        ssl->options.hrrSentCookie = 0;
9701
    #endif
9702
0
        ssl->options.hrrSentKeyShare = 0;
9703
0
    #endif
9704
    #ifdef WOLFSSL_DTLS
9705
        ssl->options.dtlsStateful = 0;
9706
    #endif
9707
0
    #if defined(HAVE_SESSION_TICKET) || !defined(NO_PSK)
9708
0
        ssl->options.noPskDheKe = 0;
9709
0
      #ifdef HAVE_SUPPORTED_CURVES
9710
0
        ssl->options.onlyPskDheKe = 0;
9711
0
      #endif
9712
0
    #endif
9713
0
    #ifdef HAVE_SESSION_TICKET
9714
0
        #ifdef WOLFSSL_TLS13
9715
0
        ssl->options.ticketsSent = 0;
9716
0
        #endif
9717
0
        ssl->options.rejectTicket = 0;
9718
0
    #endif
9719
    #ifdef WOLFSSL_EARLY_DATA
9720
        ssl->earlyData = no_early_data;
9721
        ssl->earlyDataSz = 0;
9722
    #endif
9723
9724
0
    #if defined(HAVE_TLS_EXTENSIONS) && !defined(NO_TLS)
9725
0
        TLSX_FreeAll(ssl->extensions, ssl->heap);
9726
0
        ssl->extensions = NULL;
9727
0
    #endif
9728
9729
0
        if (ssl->keys.encryptionOn) {
9730
0
            ForceZero(ssl->buffers.inputBuffer.buffer -
9731
0
                ssl->buffers.inputBuffer.offset,
9732
0
                ssl->buffers.inputBuffer.bufferSize);
9733
        #ifdef WOLFSSL_CHECK_MEM_ZERO
9734
            wc_MemZero_Check(ssl->buffers.inputBuffer.buffer -
9735
                ssl->buffers.inputBuffer.offset,
9736
                ssl->buffers.inputBuffer.bufferSize);
9737
        #endif
9738
0
        }
9739
0
        ssl->keys.encryptionOn = 0;
9740
0
        XMEMSET(&ssl->msgsReceived, 0, sizeof(ssl->msgsReceived));
9741
9742
0
        FreeCiphers(ssl);
9743
0
        InitCiphers(ssl);
9744
0
        InitCipherSpecs(&ssl->specs);
9745
9746
0
        if (InitSSL_Suites(ssl) != WOLFSSL_SUCCESS)
9747
0
            return WOLFSSL_FAILURE;
9748
9749
0
        if (InitHandshakeHashes(ssl) != 0)
9750
0
            return WOLFSSL_FAILURE;
9751
9752
0
#ifdef KEEP_PEER_CERT
9753
0
        FreeX509(&ssl->peerCert);
9754
0
        InitX509(&ssl->peerCert, 0, ssl->heap);
9755
0
#endif
9756
9757
#ifdef WOLFSSL_QUIC
9758
        wolfSSL_quic_clear(ssl);
9759
#endif
9760
0
#ifdef HAVE_OCSP
9761
#if defined(WOLFSSL_TLS13) && defined(HAVE_CERTIFICATE_STATUS_REQUEST)
9762
        ssl->response_idx = 0;
9763
#endif
9764
0
#endif
9765
0
        return WOLFSSL_SUCCESS;
9766
0
    }
9767
9768
#endif /* OPENSSL_EXTRA || WOLFSSL_WPAS_SMALL */
9769
9770
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER) || defined(HAVE_MEMCACHED)
9771
    long wolfSSL_CTX_set_mode(WOLFSSL_CTX* ctx, long mode)
9772
0
    {
9773
        /* WOLFSSL_MODE_ACCEPT_MOVING_WRITE_BUFFER is wolfSSL default mode */
9774
9775
0
        WOLFSSL_ENTER("wolfSSL_CTX_set_mode");
9776
0
        switch(mode) {
9777
0
            case WOLFSSL_MODE_ENABLE_PARTIAL_WRITE:
9778
0
                ctx->partialWrite = 1;
9779
0
                break;
9780
0
            #if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
9781
0
            case SSL_MODE_RELEASE_BUFFERS:
9782
0
                WOLFSSL_MSG("SSL_MODE_RELEASE_BUFFERS not implemented.");
9783
0
                break;
9784
0
            #endif
9785
0
            case WOLFSSL_MODE_AUTO_RETRY:
9786
0
                ctx->autoRetry = 1;
9787
0
                break;
9788
0
            default:
9789
0
                WOLFSSL_MSG("Mode Not Implemented");
9790
0
        }
9791
9792
        /* WOLFSSL_MODE_AUTO_RETRY
9793
         * Should not return WOLFSSL_FATAL_ERROR with renegotiation on read/write */
9794
9795
0
        return mode;
9796
0
    }
9797
9798
    long wolfSSL_CTX_clear_mode(WOLFSSL_CTX* ctx, long mode)
9799
0
    {
9800
        /* WOLFSSL_MODE_ACCEPT_MOVING_WRITE_BUFFER is wolfSSL default mode */
9801
9802
0
        WOLFSSL_ENTER("wolfSSL_CTX_clear_mode");
9803
0
        switch(mode) {
9804
0
            case WOLFSSL_MODE_ENABLE_PARTIAL_WRITE:
9805
0
                ctx->partialWrite = 0;
9806
0
                break;
9807
0
            #if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
9808
0
            case SSL_MODE_RELEASE_BUFFERS:
9809
0
                WOLFSSL_MSG("SSL_MODE_RELEASE_BUFFERS not implemented.");
9810
0
                break;
9811
0
            #endif
9812
0
            case WOLFSSL_MODE_AUTO_RETRY:
9813
0
                ctx->autoRetry = 0;
9814
0
                break;
9815
0
            default:
9816
0
                WOLFSSL_MSG("Mode Not Implemented");
9817
0
        }
9818
9819
        /* WOLFSSL_MODE_AUTO_RETRY
9820
         * Should not return WOLFSSL_FATAL_ERROR with renegotiation on read/write */
9821
9822
0
        return 0;
9823
0
    }
9824
#endif
9825
9826
#ifdef OPENSSL_EXTRA
9827
9828
    #ifndef NO_WOLFSSL_STUB
9829
    long wolfSSL_SSL_get_mode(WOLFSSL* ssl)
9830
0
    {
9831
        /* TODO: */
9832
0
        (void)ssl;
9833
0
        WOLFSSL_STUB("SSL_get_mode");
9834
0
        return 0;
9835
0
    }
9836
    #endif
9837
9838
    #ifndef NO_WOLFSSL_STUB
9839
    long wolfSSL_CTX_get_mode(WOLFSSL_CTX* ctx)
9840
0
    {
9841
        /* TODO: */
9842
0
        (void)ctx;
9843
0
        WOLFSSL_STUB("SSL_CTX_get_mode");
9844
0
        return 0;
9845
0
    }
9846
    #endif
9847
9848
    #ifndef NO_WOLFSSL_STUB
9849
    void wolfSSL_CTX_set_default_read_ahead(WOLFSSL_CTX* ctx, int m)
9850
0
    {
9851
        /* TODO: maybe? */
9852
0
        (void)ctx;
9853
0
        (void)m;
9854
0
        WOLFSSL_STUB("SSL_CTX_set_default_read_ahead");
9855
0
    }
9856
    #endif
9857
9858
9859
    /* returns the unsigned error value and increments the pointer into the
9860
     * error queue.
9861
     *
9862
     * file  pointer to file name
9863
     * line  gets set to line number of error when not NULL
9864
     */
9865
    unsigned long wolfSSL_ERR_get_error_line(const char** file, int* line)
9866
0
    {
9867
0
    #ifdef WOLFSSL_HAVE_ERROR_QUEUE
9868
0
        int ret = wc_PullErrorNode(file, NULL, line);
9869
0
        if (ret < 0) {
9870
0
            if (ret == WC_NO_ERR_TRACE(BAD_STATE_E))
9871
0
                return 0; /* no errors in queue */
9872
0
            WOLFSSL_MSG("Issue getting error node");
9873
0
            WOLFSSL_LEAVE("wolfSSL_ERR_get_error_line", ret);
9874
0
            ret = 0 - ret; /* return absolute value of error */
9875
9876
            /* panic and try to clear out nodes */
9877
0
            wc_ClearErrorNodes();
9878
0
        }
9879
0
        return (unsigned long)ret;
9880
    #else
9881
        (void)file;
9882
        (void)line;
9883
9884
        return 0;
9885
    #endif
9886
0
    }
9887
9888
9889
#if (defined(DEBUG_WOLFSSL) || defined(OPENSSL_EXTRA)) && \
9890
    (!defined(_WIN32) && !defined(NO_ERROR_QUEUE))
9891
    static const char WOLFSSL_SYS_ACCEPT_T[]  = "accept";
9892
    static const char WOLFSSL_SYS_BIND_T[]    = "bind";
9893
    static const char WOLFSSL_SYS_CONNECT_T[] = "connect";
9894
    static const char WOLFSSL_SYS_FOPEN_T[]   = "fopen";
9895
    static const char WOLFSSL_SYS_FREAD_T[]   = "fread";
9896
    static const char WOLFSSL_SYS_GETADDRINFO_T[] = "getaddrinfo";
9897
    static const char WOLFSSL_SYS_GETSOCKOPT_T[]  = "getsockopt";
9898
    static const char WOLFSSL_SYS_GETSOCKNAME_T[] = "getsockname";
9899
    static const char WOLFSSL_SYS_GETHOSTBYNAME_T[] = "gethostbyname";
9900
    static const char WOLFSSL_SYS_GETNAMEINFO_T[]   = "getnameinfo";
9901
    static const char WOLFSSL_SYS_GETSERVBYNAME_T[] = "getservbyname";
9902
    static const char WOLFSSL_SYS_IOCTLSOCKET_T[]   = "ioctlsocket";
9903
    static const char WOLFSSL_SYS_LISTEN_T[]        = "listen";
9904
    static const char WOLFSSL_SYS_OPENDIR_T[]       = "opendir";
9905
    static const char WOLFSSL_SYS_SETSOCKOPT_T[]    = "setsockopt";
9906
    static const char WOLFSSL_SYS_SOCKET_T[]        = "socket";
9907
9908
    /* switch with int mapped to function name for compatibility */
9909
    static const char* wolfSSL_ERR_sys_func(int fun)
9910
0
    {
9911
0
        switch (fun) {
9912
0
            case WOLFSSL_SYS_ACCEPT:      return WOLFSSL_SYS_ACCEPT_T;
9913
0
            case WOLFSSL_SYS_BIND:        return WOLFSSL_SYS_BIND_T;
9914
0
            case WOLFSSL_SYS_CONNECT:     return WOLFSSL_SYS_CONNECT_T;
9915
0
            case WOLFSSL_SYS_FOPEN:       return WOLFSSL_SYS_FOPEN_T;
9916
0
            case WOLFSSL_SYS_FREAD:       return WOLFSSL_SYS_FREAD_T;
9917
0
            case WOLFSSL_SYS_GETADDRINFO: return WOLFSSL_SYS_GETADDRINFO_T;
9918
0
            case WOLFSSL_SYS_GETSOCKOPT:  return WOLFSSL_SYS_GETSOCKOPT_T;
9919
0
            case WOLFSSL_SYS_GETSOCKNAME: return WOLFSSL_SYS_GETSOCKNAME_T;
9920
0
            case WOLFSSL_SYS_GETHOSTBYNAME: return WOLFSSL_SYS_GETHOSTBYNAME_T;
9921
0
            case WOLFSSL_SYS_GETNAMEINFO: return WOLFSSL_SYS_GETNAMEINFO_T;
9922
0
            case WOLFSSL_SYS_GETSERVBYNAME: return WOLFSSL_SYS_GETSERVBYNAME_T;
9923
0
            case WOLFSSL_SYS_IOCTLSOCKET: return WOLFSSL_SYS_IOCTLSOCKET_T;
9924
0
            case WOLFSSL_SYS_LISTEN:      return WOLFSSL_SYS_LISTEN_T;
9925
0
            case WOLFSSL_SYS_OPENDIR:     return WOLFSSL_SYS_OPENDIR_T;
9926
0
            case WOLFSSL_SYS_SETSOCKOPT:  return WOLFSSL_SYS_SETSOCKOPT_T;
9927
0
            case WOLFSSL_SYS_SOCKET:      return WOLFSSL_SYS_SOCKET_T;
9928
0
            default:
9929
0
                return "NULL";
9930
0
        }
9931
0
    }
9932
#endif /* DEBUG_WOLFSSL */
9933
9934
9935
    void wolfSSL_ERR_put_error(int lib, int fun, int err, const char* file,
9936
            int line)
9937
0
    {
9938
0
        WOLFSSL_ENTER("wolfSSL_ERR_put_error");
9939
9940
        #if !defined(DEBUG_WOLFSSL) && !defined(OPENSSL_EXTRA)
9941
        (void)fun;
9942
        (void)err;
9943
        (void)file;
9944
        (void)line;
9945
        WOLFSSL_MSG("Not compiled in debug mode");
9946
        #elif defined(OPENSSL_EXTRA) && \
9947
                (defined(_WIN32) || defined(NO_ERROR_QUEUE))
9948
        (void)fun;
9949
        (void)file;
9950
        (void)line;
9951
        WOLFSSL_ERROR(err);
9952
        #else
9953
0
        WOLFSSL_ERROR_LINE(err, wolfSSL_ERR_sys_func(fun), (unsigned int)line,
9954
0
            file, NULL);
9955
0
        #endif
9956
0
        (void)lib;
9957
0
    }
9958
9959
9960
    /* Similar to wolfSSL_ERR_get_error_line but takes in a flags argument for
9961
     * more flexibility.
9962
     *
9963
     * file  output pointer to file where error happened
9964
     * line  output to line number of error
9965
     * data  output data. Is a string if WOLFSSL_ERR_TXT_STRING flag is used
9966
     * flags output format of output
9967
     *
9968
     * Returns the error value or 0 if no errors are in the queue
9969
     */
9970
    unsigned long wolfSSL_ERR_get_error_line_data(const char** file, int* line,
9971
                                                  const char** data, int *flags)
9972
0
    {
9973
0
#ifdef WOLFSSL_HAVE_ERROR_QUEUE
9974
0
        int ret;
9975
9976
0
        WOLFSSL_ENTER("wolfSSL_ERR_get_error_line_data");
9977
9978
0
        if (flags != NULL)
9979
0
            *flags = WOLFSSL_ERR_TXT_STRING; /* Clear the flags */
9980
9981
0
        ret = wc_PullErrorNode(file, data, line);
9982
0
        if (ret < 0) {
9983
0
            if (ret == WC_NO_ERR_TRACE(BAD_STATE_E))
9984
0
                return 0; /* no errors in queue */
9985
0
            WOLFSSL_MSG("Error with pulling error node!");
9986
0
            WOLFSSL_LEAVE("wolfSSL_ERR_get_error_line_data", ret);
9987
0
            ret = 0 - ret; /* return absolute value of error */
9988
9989
            /* panic and try to clear out nodes */
9990
0
            wc_ClearErrorNodes();
9991
0
        }
9992
9993
0
        return (unsigned long)ret;
9994
#else
9995
        WOLFSSL_ENTER("wolfSSL_ERR_get_error_line_data");
9996
        WOLFSSL_MSG("Error queue turned off, can not get error line");
9997
        (void)file;
9998
        (void)line;
9999
        (void)data;
10000
        (void)flags;
10001
        return 0;
10002
#endif
10003
0
    }
10004
10005
#endif /* OPENSSL_EXTRA */
10006
10007
10008
#if (defined(KEEP_PEER_CERT) && defined(SESSION_CERTS)) || \
10009
    (defined(OPENSSL_EXTRA) && defined(SESSION_CERTS))
10010
    /* Decode the X509 DER encoded certificate into a WOLFSSL_X509 object.
10011
     *
10012
     * x509  WOLFSSL_X509 object to decode into.
10013
     * in    X509 DER data.
10014
     * len   Length of the X509 DER data.
10015
     * returns the new certificate on success, otherwise NULL.
10016
     */
10017
    static int DecodeToX509(WOLFSSL_X509* x509, const byte* in, int len)
10018
    {
10019
        int          ret;
10020
        WC_DECLARE_VAR(cert, DecodedCert, 1, 0);
10021
        if (x509 == NULL || in == NULL || len <= 0)
10022
            return BAD_FUNC_ARG;
10023
10024
        WC_ALLOC_VAR_EX(cert, DecodedCert, 1, NULL, DYNAMIC_TYPE_DCERT,
10025
            return MEMORY_E);
10026
10027
        /* Create a DecodedCert object and copy fields into WOLFSSL_X509 object.
10028
         */
10029
        InitDecodedCert(cert, (byte*)in, (word32)len, NULL);
10030
        if ((ret = ParseCertRelative(cert, CERT_TYPE, 0, NULL, NULL)) == 0) {
10031
        /* Check if x509 was not previously initialized by wolfSSL_X509_new() */
10032
            if (x509->dynamicMemory != TRUE)
10033
                InitX509(x509, 0, NULL);
10034
            ret = CopyDecodedToX509(x509, cert);
10035
        }
10036
        FreeDecodedCert(cert);
10037
        WC_FREE_VAR_EX(cert, NULL, DYNAMIC_TYPE_DCERT);
10038
10039
        return ret;
10040
    }
10041
#endif /* (KEEP_PEER_CERT & SESSION_CERTS) || (OPENSSL_EXTRA & SESSION_CERTS) */
10042
10043
10044
#ifdef KEEP_PEER_CERT
10045
    WOLFSSL_ABI
10046
    WOLFSSL_X509* wolfSSL_get_peer_certificate(WOLFSSL* ssl)
10047
0
    {
10048
0
        WOLFSSL_X509* ret = NULL;
10049
0
        WOLFSSL_ENTER("wolfSSL_get_peer_certificate");
10050
0
        if (ssl != NULL) {
10051
0
            if (ssl->peerCert.issuer.sz)
10052
0
                ret = wolfSSL_X509_dup(&ssl->peerCert);
10053
#ifdef SESSION_CERTS
10054
            else if (ssl->session->chain.count > 0) {
10055
                if (DecodeToX509(&ssl->peerCert,
10056
                        ssl->session->chain.certs[0].buffer,
10057
                        ssl->session->chain.certs[0].length) == 0) {
10058
                    ret = wolfSSL_X509_dup(&ssl->peerCert);
10059
                }
10060
            }
10061
#endif
10062
0
        }
10063
0
        WOLFSSL_LEAVE("wolfSSL_get_peer_certificate", ret != NULL);
10064
0
        return ret;
10065
0
    }
10066
10067
#endif /* KEEP_PEER_CERT */
10068
10069
#if defined(SESSION_CERTS) && defined(OPENSSL_EXTRA)
10070
/* Return stack of peer certs.
10071
 * Caller does not need to free return. The stack is Free'd when WOLFSSL* ssl
10072
 * is.
10073
 */
10074
WOLF_STACK_OF(WOLFSSL_X509)* wolfSSL_get_peer_cert_chain(const WOLFSSL* ssl)
10075
{
10076
    WOLFSSL_ENTER("wolfSSL_get_peer_cert_chain");
10077
10078
    if (ssl == NULL)
10079
        return NULL;
10080
10081
    /* Try to populate if NULL or empty */
10082
    if (ssl->peerCertChain == NULL ||
10083
            wolfSSL_sk_X509_num(ssl->peerCertChain) == 0) {
10084
        wolfSSL_set_peer_cert_chain((WOLFSSL*) ssl);
10085
    }
10086
    return ssl->peerCertChain;
10087
}
10088
10089
10090
static int x509GetIssuerFromCM(WOLFSSL_X509 **issuer, WOLFSSL_CERT_MANAGER* cm,
10091
        WOLFSSL_X509 *x);
10092
/**
10093
 * Recursively push the issuer CA chain onto the stack
10094
 * @param cm The cert manager that is queried for the issuer
10095
 * @param x  This cert's issuer will be queried in cm
10096
 * @param sk The issuer is pushed onto this stack
10097
 * @return 0 on success or no issuer found
10098
 *         WOLFSSL_FATAL_ERROR on a fatal error
10099
 */
10100
static int PushCAx509Chain(WOLFSSL_CERT_MANAGER* cm,
10101
        WOLFSSL_X509 *x, WOLFSSL_STACK* sk)
10102
{
10103
    int i;
10104
    for (i = 0; i < MAX_CHAIN_DEPTH; i++) {
10105
        WOLFSSL_X509* issuer = NULL;
10106
        if (x509GetIssuerFromCM(&issuer, cm, x) != WOLFSSL_SUCCESS)
10107
            break;
10108
        if (wolfSSL_sk_X509_push(sk, issuer) <= 0) {
10109
            wolfSSL_X509_free(issuer);
10110
            issuer = NULL;
10111
            return WOLFSSL_FATAL_ERROR;
10112
        }
10113
        x = issuer;
10114
    }
10115
    return 0;
10116
}
10117
10118
10119
/* Builds up and creates a stack of peer certificates for ssl->peerCertChain
10120
    or ssl->verifiedChain based off of the ssl session chain. Attempts to place
10121
    CA certificates at the bottom of the stack for a verified chain. Returns
10122
    stack of WOLFSSL_X509 certs or NULL on failure */
10123
static WOLF_STACK_OF(WOLFSSL_X509)* CreatePeerCertChain(const WOLFSSL* ssl,
10124
    int verifiedFlag)
10125
{
10126
    WOLFSSL_STACK* sk;
10127
    WOLFSSL_X509* x509;
10128
    int i = 0;
10129
    int err;
10130
10131
    WOLFSSL_ENTER("wolfSSL_set_peer_cert_chain");
10132
    if ((ssl == NULL) || (ssl->session->chain.count == 0))
10133
        return NULL;
10134
10135
    sk = wolfSSL_sk_X509_new_null();
10136
    for (i = 0; i < ssl->session->chain.count; i++) {
10137
        x509 = wolfSSL_X509_new_ex(ssl->heap);
10138
        if (x509 == NULL) {
10139
            WOLFSSL_MSG("Error Creating X509");
10140
            wolfSSL_sk_X509_pop_free(sk, NULL);
10141
            return NULL;
10142
        }
10143
        err = DecodeToX509(x509, ssl->session->chain.certs[i].buffer,
10144
                             ssl->session->chain.certs[i].length);
10145
        if (err == 0 && wolfSSL_sk_X509_push(sk, x509) <= 0)
10146
            err = WOLFSSL_FATAL_ERROR;
10147
        if (err == 0 && i == ssl->session->chain.count-1 && verifiedFlag) {
10148
            /* On the last element in the verified chain try to add the CA chain
10149
             * if we have one for this cert */
10150
            SSL_CM_WARNING(ssl);
10151
            err = PushCAx509Chain(SSL_CM(ssl), x509, sk);
10152
        }
10153
        if (err != 0) {
10154
            WOLFSSL_MSG("Error decoding cert");
10155
            wolfSSL_X509_free(x509);
10156
            x509 = NULL;
10157
            wolfSSL_sk_X509_pop_free(sk, NULL);
10158
            return NULL;
10159
        }
10160
    }
10161
10162
    if (sk == NULL) {
10163
        WOLFSSL_MSG("Null session chain");
10164
    }
10165
    return sk;
10166
}
10167
10168
10169
/* Builds up and creates a stack of peer certificates for ssl->peerCertChain
10170
    returns the stack on success and NULL on failure */
10171
WOLF_STACK_OF(WOLFSSL_X509)* wolfSSL_set_peer_cert_chain(WOLFSSL* ssl)
10172
{
10173
    WOLFSSL_STACK* sk;
10174
10175
    WOLFSSL_ENTER("wolfSSL_set_peer_cert_chain");
10176
    if ((ssl == NULL) || (ssl->session->chain.count == 0))
10177
        return NULL;
10178
10179
    sk = CreatePeerCertChain(ssl, 0);
10180
10181
    if (sk != NULL) {
10182
        if (ssl->options.side == WOLFSSL_SERVER_END) {
10183
            if (ssl->session->peer)
10184
                wolfSSL_X509_free(ssl->session->peer);
10185
10186
            ssl->session->peer = wolfSSL_sk_X509_shift(sk);
10187
            ssl->session->peerVerifyRet = ssl->peerVerifyRet;
10188
        }
10189
        if (ssl->peerCertChain != NULL)
10190
            wolfSSL_sk_X509_pop_free(ssl->peerCertChain, NULL);
10191
        /* This is Free'd when ssl is Free'd */
10192
        ssl->peerCertChain = sk;
10193
    }
10194
    return sk;
10195
}
10196
10197
#ifdef KEEP_PEER_CERT
10198
/**
10199
 * Implemented in a similar way that ngx_ssl_ocsp_validate does it when
10200
 * SSL_get0_verified_chain is not available.
10201
 * @param ssl WOLFSSL object to extract certs from
10202
 * @return Stack of verified certs
10203
 */
10204
WOLF_STACK_OF(WOLFSSL_X509) *wolfSSL_get0_verified_chain(const WOLFSSL *ssl)
10205
{
10206
    WOLF_STACK_OF(WOLFSSL_X509)* chain = NULL;
10207
    WOLFSSL_X509_STORE_CTX* storeCtx = NULL;
10208
    WOLFSSL_X509* peerCert = NULL;
10209
10210
    WOLFSSL_ENTER("wolfSSL_get0_verified_chain");
10211
10212
    if (ssl == NULL || ssl->ctx == NULL) {
10213
        WOLFSSL_MSG("Bad parameter");
10214
        return NULL;
10215
    }
10216
10217
    peerCert = wolfSSL_get_peer_certificate((WOLFSSL*)ssl);
10218
    if (peerCert == NULL) {
10219
        WOLFSSL_MSG("wolfSSL_get_peer_certificate error");
10220
        return NULL;
10221
    }
10222
    /* wolfSSL_get_peer_certificate returns a copy. We want the internal
10223
     * member so that we don't have to worry about free'ing it. We call
10224
     * wolfSSL_get_peer_certificate so that we don't have to worry about
10225
     * setting up the internal pointer. */
10226
    wolfSSL_X509_free(peerCert);
10227
    peerCert = (WOLFSSL_X509*)&ssl->peerCert;
10228
    chain = CreatePeerCertChain((WOLFSSL*)ssl, 1);
10229
    if (chain == NULL) {
10230
        WOLFSSL_MSG("wolfSSL_get_peer_cert_chain error");
10231
        return NULL;
10232
    }
10233
10234
    if (ssl->verifiedChain != NULL) {
10235
        wolfSSL_sk_X509_pop_free(ssl->verifiedChain, NULL);
10236
    }
10237
    ((WOLFSSL*)ssl)->verifiedChain = chain;
10238
10239
    storeCtx = wolfSSL_X509_STORE_CTX_new();
10240
    if (storeCtx == NULL) {
10241
        WOLFSSL_MSG("wolfSSL_X509_STORE_CTX_new error");
10242
        return NULL;
10243
    }
10244
    if (wolfSSL_X509_STORE_CTX_init(storeCtx, SSL_STORE(ssl),
10245
            peerCert, chain) != WOLFSSL_SUCCESS) {
10246
        WOLFSSL_MSG("wolfSSL_X509_STORE_CTX_init error");
10247
        wolfSSL_X509_STORE_CTX_free(storeCtx);
10248
        return NULL;
10249
    }
10250
    if (wolfSSL_X509_verify_cert(storeCtx) <= 0) {
10251
        WOLFSSL_MSG("wolfSSL_X509_verify_cert error");
10252
        wolfSSL_X509_STORE_CTX_free(storeCtx);
10253
        return NULL;
10254
    }
10255
    wolfSSL_X509_STORE_CTX_free(storeCtx);
10256
    return chain;
10257
}
10258
#endif /* KEEP_PEER_CERT */
10259
#endif /* SESSION_CERTS && OPENSSL_EXTRA */
10260
10261
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
10262
void wolfSSL_set_connect_state(WOLFSSL* ssl)
10263
0
{
10264
0
    WOLFSSL_ENTER("wolfSSL_set_connect_state");
10265
0
    if (ssl == NULL) {
10266
0
        WOLFSSL_MSG("WOLFSSL struct pointer passed in was null");
10267
0
        return;
10268
0
    }
10269
10270
0
    #ifndef NO_DH
10271
    /* client creates its own DH parameters on handshake */
10272
0
    if (ssl->buffers.serverDH_P.buffer && ssl->buffers.weOwnDH) {
10273
0
        XFREE(ssl->buffers.serverDH_P.buffer, ssl->heap,
10274
0
            DYNAMIC_TYPE_PUBLIC_KEY);
10275
0
    }
10276
0
    ssl->buffers.serverDH_P.buffer = NULL;
10277
0
    if (ssl->buffers.serverDH_G.buffer && ssl->buffers.weOwnDH) {
10278
0
        XFREE(ssl->buffers.serverDH_G.buffer, ssl->heap,
10279
0
            DYNAMIC_TYPE_PUBLIC_KEY);
10280
0
    }
10281
0
    ssl->buffers.serverDH_G.buffer = NULL;
10282
0
    #endif
10283
10284
0
    if (InitSSL_Side(ssl, WOLFSSL_CLIENT_END) != WOLFSSL_SUCCESS) {
10285
0
        WOLFSSL_MSG("Error initializing client side");
10286
0
    }
10287
0
}
10288
#endif /* OPENSSL_EXTRA || WOLFSSL_WPAS_SMALL */
10289
10290
10291
int wolfSSL_get_shutdown(const WOLFSSL* ssl)
10292
0
{
10293
0
    int isShutdown = 0;
10294
10295
0
    WOLFSSL_ENTER("wolfSSL_get_shutdown");
10296
10297
0
    if (ssl) {
10298
0
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
10299
0
        if (ssl->options.shutdownDone) {
10300
            /* The SSL object was possibly cleared with wolfSSL_clear after
10301
             * a successful shutdown. Simulate a response for a full
10302
             * bidirectional shutdown. */
10303
0
            isShutdown = WOLFSSL_SENT_SHUTDOWN | WOLFSSL_RECEIVED_SHUTDOWN;
10304
0
        }
10305
0
        else
10306
0
#endif
10307
0
        {
10308
            /* in OpenSSL, WOLFSSL_SENT_SHUTDOWN = 1, when closeNotifySent   *
10309
             * WOLFSSL_RECEIVED_SHUTDOWN = 2, from close notify or fatal err */
10310
0
            if (ssl->options.sentNotify)
10311
0
                isShutdown |= WOLFSSL_SENT_SHUTDOWN;
10312
0
            if (ssl->options.closeNotify||ssl->options.connReset)
10313
0
                isShutdown |= WOLFSSL_RECEIVED_SHUTDOWN;
10314
0
        }
10315
10316
0
    }
10317
10318
0
    WOLFSSL_LEAVE("wolfSSL_get_shutdown", isShutdown);
10319
0
    return isShutdown;
10320
0
}
10321
10322
10323
int wolfSSL_session_reused(WOLFSSL* ssl)
10324
0
{
10325
0
    int resuming = 0;
10326
0
    WOLFSSL_ENTER("wolfSSL_session_reused");
10327
0
    if (ssl) {
10328
0
#ifndef HAVE_SECURE_RENEGOTIATION
10329
0
        resuming = ssl->options.resuming;
10330
#else
10331
        resuming = ssl->options.resuming || ssl->options.resumed;
10332
#endif
10333
0
    }
10334
0
    WOLFSSL_LEAVE("wolfSSL_session_reused", resuming);
10335
0
    return resuming;
10336
0
}
10337
10338
/* helper function that takes in a protocol version struct and returns string */
10339
static const char* wolfSSL_internal_get_version(const ProtocolVersion* version)
10340
0
{
10341
0
    WOLFSSL_ENTER("wolfSSL_get_version");
10342
10343
0
    if (version == NULL) {
10344
0
        return "Bad arg";
10345
0
    }
10346
10347
0
    if (version->major == SSLv3_MAJOR) {
10348
0
        switch (version->minor) {
10349
0
            case SSLv3_MINOR :
10350
0
                return "SSLv3";
10351
0
            case TLSv1_MINOR :
10352
0
                return "TLSv1";
10353
0
            case TLSv1_1_MINOR :
10354
0
                return "TLSv1.1";
10355
0
            case TLSv1_2_MINOR :
10356
0
                return "TLSv1.2";
10357
0
            case TLSv1_3_MINOR :
10358
0
                return "TLSv1.3";
10359
0
            default:
10360
0
                return "unknown";
10361
0
        }
10362
0
    }
10363
#ifdef WOLFSSL_DTLS
10364
    else if (version->major == DTLS_MAJOR) {
10365
        switch (version->minor) {
10366
            case DTLS_MINOR :
10367
                return "DTLS";
10368
            case DTLSv1_2_MINOR :
10369
                return "DTLSv1.2";
10370
            case DTLSv1_3_MINOR :
10371
                return "DTLSv1.3";
10372
            default:
10373
                return "unknown";
10374
        }
10375
    }
10376
#endif /* WOLFSSL_DTLS */
10377
0
    return "unknown";
10378
0
}
10379
10380
10381
const char* wolfSSL_get_version(const WOLFSSL* ssl)
10382
0
{
10383
0
    if (ssl == NULL) {
10384
0
        WOLFSSL_MSG("Bad argument");
10385
0
        return "unknown";
10386
0
    }
10387
10388
0
    return wolfSSL_internal_get_version(&ssl->version);
10389
0
}
10390
10391
10392
/* current library version */
10393
const char* wolfSSL_lib_version(void)
10394
0
{
10395
0
    return LIBWOLFSSL_VERSION_STRING;
10396
0
}
10397
10398
#ifdef OPENSSL_EXTRA
10399
#if defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x10100000L
10400
const char* wolfSSL_OpenSSL_version(int a)
10401
{
10402
    (void)a;
10403
    return "wolfSSL " LIBWOLFSSL_VERSION_STRING;
10404
}
10405
#else
10406
const char* wolfSSL_OpenSSL_version(void)
10407
0
{
10408
0
    return "wolfSSL " LIBWOLFSSL_VERSION_STRING;
10409
0
}
10410
#endif /* WOLFSSL_QT */
10411
#endif
10412
10413
10414
/* current library version in hex */
10415
word32 wolfSSL_lib_version_hex(void)
10416
0
{
10417
0
    return LIBWOLFSSL_VERSION_HEX;
10418
0
}
10419
10420
10421
int wolfSSL_get_current_cipher_suite(WOLFSSL* ssl)
10422
0
{
10423
0
    WOLFSSL_ENTER("wolfSSL_get_current_cipher_suite");
10424
0
    if (ssl)
10425
0
        return (ssl->options.cipherSuite0 << 8) | ssl->options.cipherSuite;
10426
0
    return 0;
10427
0
}
10428
10429
WOLFSSL_CIPHER* wolfSSL_get_current_cipher(WOLFSSL* ssl)
10430
0
{
10431
0
    WOLFSSL_ENTER("wolfSSL_get_current_cipher");
10432
0
    if (ssl) {
10433
0
        ssl->cipher.cipherSuite0 = ssl->options.cipherSuite0;
10434
0
        ssl->cipher.cipherSuite  = ssl->options.cipherSuite;
10435
0
#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
10436
0
        ssl->cipher.bits = ssl->specs.key_size * 8;
10437
0
#endif
10438
0
        return &ssl->cipher;
10439
0
    }
10440
0
    else
10441
0
        return NULL;
10442
0
}
10443
10444
10445
const char* wolfSSL_CIPHER_get_name(const WOLFSSL_CIPHER* cipher)
10446
0
{
10447
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_name");
10448
10449
0
    if (cipher == NULL) {
10450
0
        return NULL;
10451
0
    }
10452
10453
0
    #if !defined(WOLFSSL_CIPHER_INTERNALNAME) && !defined(NO_ERROR_STRINGS) && \
10454
0
        !defined(WOLFSSL_QT)
10455
0
        return GetCipherNameIana(cipher->cipherSuite0, cipher->cipherSuite);
10456
    #else
10457
        return wolfSSL_get_cipher_name_from_suite(cipher->cipherSuite0,
10458
                cipher->cipherSuite);
10459
    #endif
10460
0
}
10461
10462
const char*  wolfSSL_CIPHER_get_version(const WOLFSSL_CIPHER* cipher)
10463
0
{
10464
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_version");
10465
10466
0
    if (cipher == NULL || cipher->ssl == NULL) {
10467
0
        return NULL;
10468
0
    }
10469
10470
0
    return wolfSSL_get_version(cipher->ssl);
10471
0
}
10472
10473
const char* wolfSSL_get_cipher(WOLFSSL* ssl)
10474
0
{
10475
0
    WOLFSSL_ENTER("wolfSSL_get_cipher");
10476
0
    return wolfSSL_CIPHER_get_name(wolfSSL_get_current_cipher(ssl));
10477
0
}
10478
10479
/* gets cipher name in the format DHE-RSA-... rather then TLS_DHE... */
10480
const char* wolfSSL_get_cipher_name(WOLFSSL* ssl)
10481
0
{
10482
    /* get access to cipher_name_idx in internal.c */
10483
0
    return wolfSSL_get_cipher_name_internal(ssl);
10484
0
}
10485
10486
const char* wolfSSL_get_cipher_name_from_suite(byte cipherSuite0,
10487
    byte cipherSuite)
10488
0
{
10489
0
    return GetCipherNameInternal(cipherSuite0, cipherSuite);
10490
0
}
10491
10492
const char* wolfSSL_get_cipher_name_iana_from_suite(byte cipherSuite0,
10493
        byte cipherSuite)
10494
0
{
10495
0
    return GetCipherNameIana(cipherSuite0, cipherSuite);
10496
0
}
10497
10498
int wolfSSL_get_cipher_suite_from_name(const char* name, byte* cipherSuite0,
10499
0
                                       byte* cipherSuite, int *flags) {
10500
0
    if ((name == NULL) ||
10501
0
        (cipherSuite0 == NULL) ||
10502
0
        (cipherSuite == NULL) ||
10503
0
        (flags == NULL))
10504
0
        return BAD_FUNC_ARG;
10505
0
    return GetCipherSuiteFromName(name, cipherSuite0, cipherSuite, NULL, NULL,
10506
0
                                  flags);
10507
0
}
10508
10509
10510
word32 wolfSSL_CIPHER_get_id(const WOLFSSL_CIPHER* cipher)
10511
0
{
10512
0
    word16 cipher_id = 0;
10513
10514
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_id");
10515
10516
0
    if (cipher && cipher->ssl) {
10517
0
        cipher_id = (word16)(cipher->ssl->options.cipherSuite0 << 8) |
10518
0
                     cipher->ssl->options.cipherSuite;
10519
0
    }
10520
10521
0
    return cipher_id;
10522
0
}
10523
10524
const WOLFSSL_CIPHER* wolfSSL_get_cipher_by_value(word16 value)
10525
0
{
10526
0
    const WOLFSSL_CIPHER* cipher = NULL;
10527
0
    byte cipherSuite0, cipherSuite;
10528
0
    WOLFSSL_ENTER("wolfSSL_get_cipher_by_value");
10529
10530
    /* extract cipher id information */
10531
0
    cipherSuite =   (value       & 0xFF);
10532
0
    cipherSuite0 = ((value >> 8) & 0xFF);
10533
10534
    /* TODO: lookup by cipherSuite0 / cipherSuite */
10535
0
    (void)cipherSuite0;
10536
0
    (void)cipherSuite;
10537
10538
0
    return cipher;
10539
0
}
10540
10541
10542
#if defined(HAVE_ECC) || defined(HAVE_CURVE25519) || defined(HAVE_CURVE448) || \
10543
                                                                 !defined(NO_DH)
10544
#ifdef HAVE_FFDHE
10545
static const char* wolfssl_ffdhe_name(word16 group)
10546
0
{
10547
0
    const char* str = NULL;
10548
0
    switch (group) {
10549
0
        case WOLFSSL_FFDHE_2048:
10550
0
            str = "FFDHE_2048";
10551
0
            break;
10552
0
        case WOLFSSL_FFDHE_3072:
10553
0
            str = "FFDHE_3072";
10554
0
            break;
10555
0
        case WOLFSSL_FFDHE_4096:
10556
0
            str = "FFDHE_4096";
10557
0
            break;
10558
0
        case WOLFSSL_FFDHE_6144:
10559
0
            str = "FFDHE_6144";
10560
0
            break;
10561
0
        case WOLFSSL_FFDHE_8192:
10562
0
            str = "FFDHE_8192";
10563
0
            break;
10564
0
        default:
10565
0
            break;
10566
0
    }
10567
0
    return str;
10568
0
}
10569
#endif
10570
/* Return the name of the curve used for key exchange as a printable string.
10571
 *
10572
 * ssl  The SSL/TLS object.
10573
 * returns NULL if ECDH was not used, otherwise the name as a string.
10574
 */
10575
const char* wolfSSL_get_curve_name(WOLFSSL* ssl)
10576
0
{
10577
0
    const char* cName = NULL;
10578
10579
0
    WOLFSSL_ENTER("wolfSSL_get_curve_name");
10580
10581
0
    if (ssl == NULL)
10582
0
        return NULL;
10583
10584
#if defined(WOLFSSL_TLS13) && defined(WOLFSSL_HAVE_MLKEM)
10585
    /* Check for post-quantum groups. Return now because we do not want the ECC
10586
     * check to override this result in the case of a hybrid. */
10587
    if (IsAtLeastTLSv1_3(ssl->version)) {
10588
        switch (ssl->namedGroup) {
10589
#ifndef WOLFSSL_NO_ML_KEM
10590
#if defined(WOLFSSL_WC_MLKEM)
10591
    #ifndef WOLFSSL_NO_ML_KEM_512
10592
        case WOLFSSL_ML_KEM_512:
10593
            return "ML_KEM_512";
10594
        case WOLFSSL_SECP256R1MLKEM512:
10595
            return "SecP256r1MLKEM512";
10596
#ifdef WOLFSSL_ML_KEM_USE_OLD_IDS
10597
        case WOLFSSL_P256_ML_KEM_512_OLD:
10598
            return "P256_ML_KEM_512_OLD";
10599
#endif
10600
        #ifdef HAVE_CURVE25519
10601
        case WOLFSSL_X25519MLKEM512:
10602
            return "X25519MLKEM512";
10603
        #endif
10604
    #endif
10605
    #ifndef WOLFSSL_NO_ML_KEM_768
10606
        case WOLFSSL_ML_KEM_768:
10607
            return "ML_KEM_768";
10608
        case WOLFSSL_SECP384R1MLKEM768:
10609
            return "SecP384r1MLKEM768";
10610
#ifdef WOLFSSL_ML_KEM_USE_OLD_IDS
10611
        case WOLFSSL_P384_ML_KEM_768_OLD:
10612
            return "P384_ML_KEM_768_OLD";
10613
#endif
10614
        case WOLFSSL_SECP256R1MLKEM768:
10615
            return "SecP256r1MLKEM768";
10616
        #ifdef HAVE_CURVE25519
10617
        case WOLFSSL_X25519MLKEM768:
10618
            return "X25519MLKEM768";
10619
        #endif
10620
        #ifdef HAVE_CURVE448
10621
        case WOLFSSL_X448MLKEM768:
10622
            return "X448MLKEM768";
10623
        #endif
10624
    #endif
10625
    #ifndef WOLFSSL_NO_ML_KEM_1024
10626
        case WOLFSSL_ML_KEM_1024:
10627
            return "ML_KEM_1024";
10628
        case WOLFSSL_SECP521R1MLKEM1024:
10629
            return "SecP521r1MLKEM1024";
10630
#ifdef WOLFSSL_ML_KEM_USE_OLD_IDS
10631
        case WOLFSSL_P521_ML_KEM_1024_OLD:
10632
            return "P521_ML_KEM_1024_OLD";
10633
#endif
10634
        case WOLFSSL_SECP384R1MLKEM1024:
10635
            return "SecP384r1MLKEM1024";
10636
    #endif
10637
#elif defined(HAVE_LIBOQS)
10638
        case WOLFSSL_ML_KEM_512:
10639
            return "ML_KEM_512";
10640
        case WOLFSSL_ML_KEM_768:
10641
            return "ML_KEM_768";
10642
        case WOLFSSL_ML_KEM_1024:
10643
            return "ML_KEM_1024";
10644
        case WOLFSSL_SECP256R1MLKEM512:
10645
            return "SecP256r1MLKEM512";
10646
        case WOLFSSL_SECP384R1MLKEM768:
10647
            return "SecP384r1MLKEM768";
10648
        case WOLFSSL_SECP256R1MLKEM768:
10649
            return "SecP256r1MLKEM768";
10650
        case WOLFSSL_SECP521R1MLKEM1024:
10651
            return "SecP521r1MLKEM1024";
10652
        case WOLFSSL_SECP384R1MLKEM1024:
10653
            return "SecP384r1MLKEM1024";
10654
    #ifdef HAVE_CURVE25519
10655
        case WOLFSSL_X25519MLKEM512:
10656
            return "X25519MLKEM512";
10657
        case WOLFSSL_X25519MLKEM768:
10658
            return "X25519MLKEM768";
10659
    #endif
10660
    #ifdef HAVE_CURVE448
10661
        case WOLFSSL_X448MLKEM768:
10662
            return "X448MLKEM768";
10663
    #endif
10664
#endif /* WOLFSSL_WC_MLKEM */
10665
#endif /* WOLFSSL_NO_ML_KEM */
10666
#ifdef WOLFSSL_MLKEM_KYBER
10667
#if defined(WOLFSSL_WC_MLKEM)
10668
    #ifndef WOLFSSL_NO_KYBER512
10669
        case WOLFSSL_KYBER_LEVEL1:
10670
            return "KYBER_LEVEL1";
10671
        case WOLFSSL_P256_KYBER_LEVEL1:
10672
            return "P256_KYBER_LEVEL1";
10673
        #ifdef HAVE_CURVE25519
10674
        case WOLFSSL_X25519_KYBER_LEVEL1:
10675
            return "X25519_KYBER_LEVEL1";
10676
        #endif
10677
    #endif
10678
    #ifndef WOLFSSL_NO_KYBER768
10679
        case WOLFSSL_KYBER_LEVEL3:
10680
            return "KYBER_LEVEL3";
10681
        case WOLFSSL_P384_KYBER_LEVEL3:
10682
            return "P384_KYBER_LEVEL3";
10683
        case WOLFSSL_P256_KYBER_LEVEL3:
10684
            return "P256_KYBER_LEVEL3";
10685
        #ifdef HAVE_CURVE25519
10686
        case WOLFSSL_X25519_KYBER_LEVEL3:
10687
            return "X25519_KYBER_LEVEL3";
10688
        #endif
10689
        #ifdef HAVE_CURVE448
10690
        case WOLFSSL_X448_KYBER_LEVEL3:
10691
            return "X448_KYBER_LEVEL3";
10692
        #endif
10693
    #endif
10694
    #ifndef WOLFSSL_NO_KYBER1024
10695
        case WOLFSSL_KYBER_LEVEL5:
10696
            return "KYBER_LEVEL5";
10697
        case WOLFSSL_P521_KYBER_LEVEL5:
10698
            return "P521_KYBER_LEVEL5";
10699
    #endif
10700
#elif defined (HAVE_LIBOQS)
10701
        case WOLFSSL_KYBER_LEVEL1:
10702
            return "KYBER_LEVEL1";
10703
        case WOLFSSL_KYBER_LEVEL3:
10704
            return "KYBER_LEVEL3";
10705
        case WOLFSSL_KYBER_LEVEL5:
10706
            return "KYBER_LEVEL5";
10707
        case WOLFSSL_P256_KYBER_LEVEL1:
10708
            return "P256_KYBER_LEVEL1";
10709
        case WOLFSSL_P384_KYBER_LEVEL3:
10710
            return "P384_KYBER_LEVEL3";
10711
        case WOLFSSL_P256_KYBER_LEVEL3:
10712
            return "P256_KYBER_LEVEL3";
10713
        case WOLFSSL_P521_KYBER_LEVEL5:
10714
            return "P521_KYBER_LEVEL5";
10715
    #ifdef HAVE_CURVE25519
10716
        case WOLFSSL_X25519_KYBER_LEVEL1:
10717
            return "X25519_KYBER_LEVEL1";
10718
        case WOLFSSL_X25519_KYBER_LEVEL3:
10719
            return "X25519_KYBER_LEVEL3";
10720
    #endif
10721
    #ifdef HAVE_CURVE448
10722
        case WOLFSSL_X448_KYBER_LEVEL3:
10723
            return "X448_KYBER_LEVEL3";
10724
    #endif
10725
#endif /* WOLFSSL_WC_MLKEM */
10726
#endif /* WOLFSSL_MLKEM_KYBER */
10727
        }
10728
    }
10729
#endif /* WOLFSSL_TLS13 && WOLFSSL_HAVE_MLKEM */
10730
10731
0
#ifdef HAVE_FFDHE
10732
0
    if (ssl->namedGroup != 0) {
10733
0
        cName = wolfssl_ffdhe_name(ssl->namedGroup);
10734
0
    }
10735
0
#endif
10736
10737
0
#ifdef HAVE_CURVE25519
10738
0
    if (ssl->ecdhCurveOID == ECC_X25519_OID && cName == NULL) {
10739
0
        cName = "X25519";
10740
0
    }
10741
0
#endif
10742
10743
0
#ifdef HAVE_CURVE448
10744
0
    if (ssl->ecdhCurveOID == ECC_X448_OID && cName == NULL) {
10745
0
        cName = "X448";
10746
0
    }
10747
0
#endif
10748
10749
0
#ifdef HAVE_ECC
10750
0
    if (ssl->ecdhCurveOID != 0 && cName == NULL) {
10751
0
        cName = wc_ecc_get_name(wc_ecc_get_oid(ssl->ecdhCurveOID, NULL,
10752
0
                                NULL));
10753
0
    }
10754
0
#endif
10755
10756
0
    return cName;
10757
0
}
10758
#endif
10759
10760
#ifdef OPENSSL_EXTRA
10761
#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
10762
/* return authentication NID corresponding to cipher suite
10763
 * @param cipher a pointer to WOLFSSL_CIPHER
10764
 * return NID if found, WC_NID_undef if not found
10765
 */
10766
int wolfSSL_CIPHER_get_auth_nid(const WOLFSSL_CIPHER* cipher)
10767
0
{
10768
0
    static const struct authnid {
10769
0
        const char* alg_name;
10770
0
        const int  nid;
10771
0
    } authnid_tbl[] = {
10772
0
        {"RSA",     WC_NID_auth_rsa},
10773
0
        {"PSK",     WC_NID_auth_psk},
10774
0
        {"SRP",     WC_NID_auth_srp},
10775
0
        {"ECDSA",   WC_NID_auth_ecdsa},
10776
0
        {"None",    WC_NID_auth_null},
10777
0
        {NULL,      WC_NID_undef}
10778
0
    };
10779
10780
0
    const char* authStr;
10781
0
    char n[MAX_SEGMENTS][MAX_SEGMENT_SZ] = {{0}};
10782
10783
0
    if (GetCipherSegment(cipher, n) == NULL) {
10784
0
        WOLFSSL_MSG("no suitable cipher name found");
10785
0
        return WC_NID_undef;
10786
0
    }
10787
10788
0
    authStr = GetCipherAuthStr(n);
10789
10790
0
    if (authStr != NULL) {
10791
0
        const struct authnid* sa;
10792
0
        for(sa = authnid_tbl; sa->alg_name != NULL; sa++) {
10793
0
            if (XSTRCMP(sa->alg_name, authStr) == 0) {
10794
0
                return sa->nid;
10795
0
            }
10796
0
        }
10797
0
    }
10798
10799
0
    return WC_NID_undef;
10800
0
}
10801
/* return cipher NID corresponding to cipher suite
10802
 * @param cipher a pointer to WOLFSSL_CIPHER
10803
 * return NID if found, WC_NID_undef if not found
10804
 */
10805
int wolfSSL_CIPHER_get_cipher_nid(const WOLFSSL_CIPHER* cipher)
10806
0
{
10807
0
    static const struct ciphernid {
10808
0
        const char* alg_name;
10809
0
        const int  nid;
10810
0
    } ciphernid_tbl[] = {
10811
0
        {"AESGCM(256)",             WC_NID_aes_256_gcm},
10812
0
        {"AESGCM(128)",             WC_NID_aes_128_gcm},
10813
0
        {"AESCCM(128)",             WC_NID_aes_128_ccm},
10814
0
        {"AES(128)",                WC_NID_aes_128_cbc},
10815
0
        {"AES(256)",                WC_NID_aes_256_cbc},
10816
0
        {"CAMELLIA(256)",           WC_NID_camellia_256_cbc},
10817
0
        {"CAMELLIA(128)",           WC_NID_camellia_128_cbc},
10818
0
        {"RC4",                     WC_NID_rc4},
10819
0
        {"3DES",                    WC_NID_des_ede3_cbc},
10820
0
        {"CHACHA20/POLY1305(256)",  WC_NID_chacha20_poly1305},
10821
0
        {"None",                    WC_NID_undef},
10822
0
        {NULL,                      WC_NID_undef}
10823
0
    };
10824
10825
0
    const char* encStr;
10826
0
    char n[MAX_SEGMENTS][MAX_SEGMENT_SZ] = {{0}};
10827
10828
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_cipher_nid");
10829
10830
0
    if (GetCipherSegment(cipher, n) == NULL) {
10831
0
        WOLFSSL_MSG("no suitable cipher name found");
10832
0
        return WC_NID_undef;
10833
0
    }
10834
10835
0
    encStr = GetCipherEncStr(n);
10836
10837
0
    if (encStr != NULL) {
10838
0
        const struct ciphernid* c;
10839
0
        for(c = ciphernid_tbl; c->alg_name != NULL; c++) {
10840
0
            if (XSTRCMP(c->alg_name, encStr) == 0) {
10841
0
                return c->nid;
10842
0
            }
10843
0
        }
10844
0
    }
10845
10846
0
    return WC_NID_undef;
10847
0
}
10848
/* return digest NID corresponding to cipher suite
10849
 * @param cipher a pointer to WOLFSSL_CIPHER
10850
 * return NID if found, WC_NID_undef if not found
10851
 */
10852
int wolfSSL_CIPHER_get_digest_nid(const WOLFSSL_CIPHER* cipher)
10853
0
{
10854
0
    static const struct macnid {
10855
0
        const char* alg_name;
10856
0
        const int  nid;
10857
0
    } macnid_tbl[] = {
10858
0
        {"SHA1",    WC_NID_sha1},
10859
0
        {"SHA256",  WC_NID_sha256},
10860
0
        {"SHA384",  WC_NID_sha384},
10861
0
        {NULL,      WC_NID_undef}
10862
0
    };
10863
10864
0
    const char* name;
10865
0
    const char* macStr;
10866
0
    char n[MAX_SEGMENTS][MAX_SEGMENT_SZ] = {{0}};
10867
0
    (void)name;
10868
10869
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_digest_nid");
10870
10871
0
    if ((name = GetCipherSegment(cipher, n)) == NULL) {
10872
0
        WOLFSSL_MSG("no suitable cipher name found");
10873
0
        return WC_NID_undef;
10874
0
    }
10875
10876
    /* in MD5 case, NID will be WC_NID_md5 */
10877
0
    if (XSTRSTR(name, "MD5") != NULL) {
10878
0
        return WC_NID_md5;
10879
0
    }
10880
10881
0
    macStr = GetCipherMacStr(n);
10882
10883
0
    if (macStr != NULL) {
10884
0
        const struct macnid* mc;
10885
0
        for(mc = macnid_tbl; mc->alg_name != NULL; mc++) {
10886
0
            if (XSTRCMP(mc->alg_name, macStr) == 0) {
10887
0
                return mc->nid;
10888
0
            }
10889
0
        }
10890
0
    }
10891
10892
0
    return WC_NID_undef;
10893
0
}
10894
/* return key exchange NID corresponding to cipher suite
10895
 * @param cipher a pointer to WOLFSSL_CIPHER
10896
 * return NID if found, WC_NID_undef if not found
10897
 */
10898
int wolfSSL_CIPHER_get_kx_nid(const WOLFSSL_CIPHER* cipher)
10899
0
{
10900
0
    static const struct kxnid {
10901
0
        const char* name;
10902
0
        const int  nid;
10903
0
    } kxnid_table[] = {
10904
0
        {"ECDHEPSK",  WC_NID_kx_ecdhe_psk},
10905
0
        {"ECDH",      WC_NID_kx_ecdhe},
10906
0
        {"DHEPSK",    WC_NID_kx_dhe_psk},
10907
0
        {"DH",        WC_NID_kx_dhe},
10908
0
        {"RSAPSK",    WC_NID_kx_rsa_psk},
10909
0
        {"SRP",       WC_NID_kx_srp},
10910
0
        {"EDH",       WC_NID_kx_dhe},
10911
0
        {"RSA",       WC_NID_kx_rsa},
10912
0
        {NULL,        WC_NID_undef}
10913
0
    };
10914
10915
0
    const char* keaStr;
10916
0
    char n[MAX_SEGMENTS][MAX_SEGMENT_SZ] = {{0}};
10917
10918
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_kx_nid");
10919
10920
0
    if (GetCipherSegment(cipher, n) == NULL) {
10921
0
        WOLFSSL_MSG("no suitable cipher name found");
10922
0
        return WC_NID_undef;
10923
0
    }
10924
10925
    /* in TLS 1.3 case, NID will be WC_NID_kx_any */
10926
0
    if (XSTRCMP(n[0], "TLS13") == 0) {
10927
0
        return WC_NID_kx_any;
10928
0
    }
10929
10930
0
    keaStr = GetCipherKeaStr(n);
10931
10932
0
    if (keaStr != NULL) {
10933
0
        const struct kxnid* k;
10934
0
        for(k = kxnid_table; k->name != NULL; k++) {
10935
0
            if (XSTRCMP(k->name, keaStr) == 0) {
10936
0
                return k->nid;
10937
0
            }
10938
0
        }
10939
0
    }
10940
10941
0
    return WC_NID_undef;
10942
0
}
10943
/* check if cipher suite is AEAD
10944
 * @param cipher a pointer to WOLFSSL_CIPHER
10945
 * return 1 if cipher is AEAD, 0 otherwise
10946
 */
10947
int wolfSSL_CIPHER_is_aead(const WOLFSSL_CIPHER* cipher)
10948
0
{
10949
0
    char n[MAX_SEGMENTS][MAX_SEGMENT_SZ] = {{0}};
10950
10951
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_is_aead");
10952
10953
0
    if (GetCipherSegment(cipher, n) == NULL) {
10954
0
        WOLFSSL_MSG("no suitable cipher name found");
10955
0
        return WC_NID_undef;
10956
0
    }
10957
10958
0
    return IsCipherAEAD(n);
10959
0
}
10960
/* Creates cipher->description based on cipher->offset
10961
 * cipher->offset is set in wolfSSL_get_ciphers_compat when it is added
10962
 * to a stack of ciphers.
10963
 * @param [in] cipher: A cipher from a stack of ciphers.
10964
 * return WOLFSSL_SUCCESS if cipher->description is set, else WOLFSSL_FAILURE
10965
 */
10966
int wolfSSL_sk_CIPHER_description(WOLFSSL_CIPHER* cipher)
10967
0
{
10968
0
    int strLen;
10969
0
    unsigned long offset;
10970
0
    char* dp;
10971
0
    const char* name;
10972
0
    const char *keaStr, *authStr, *encStr, *macStr, *protocol;
10973
0
    char n[MAX_SEGMENTS][MAX_SEGMENT_SZ] = {{0}};
10974
0
    int len = MAX_DESCRIPTION_SZ-1;
10975
0
    const CipherSuiteInfo* cipher_names;
10976
0
    ProtocolVersion pv;
10977
0
    WOLFSSL_ENTER("wolfSSL_sk_CIPHER_description");
10978
10979
0
    if (cipher == NULL)
10980
0
        return WOLFSSL_FAILURE;
10981
10982
0
    dp = cipher->description;
10983
0
    if (dp == NULL)
10984
0
        return WOLFSSL_FAILURE;
10985
10986
0
    cipher_names = GetCipherNames();
10987
10988
0
    offset = cipher->offset;
10989
0
    if (offset >= (unsigned long)GetCipherNamesSize())
10990
0
        return WOLFSSL_FAILURE;
10991
0
    pv.major = cipher_names[offset].major;
10992
0
    pv.minor = cipher_names[offset].minor;
10993
0
    protocol = wolfSSL_internal_get_version(&pv);
10994
10995
0
    if ((name = GetCipherSegment(cipher, n)) == NULL) {
10996
0
        WOLFSSL_MSG("no suitable cipher name found");
10997
0
        return WOLFSSL_FAILURE;
10998
0
    }
10999
11000
    /* keaStr */
11001
0
    keaStr = GetCipherKeaStr(n);
11002
    /* authStr */
11003
0
    authStr = GetCipherAuthStr(n);
11004
    /* encStr */
11005
0
    encStr = GetCipherEncStr(n);
11006
0
    if ((cipher->bits = SetCipherBits(encStr)) ==
11007
0
        WC_NO_ERR_TRACE(WOLFSSL_FAILURE))
11008
0
    {
11009
0
       WOLFSSL_MSG("Cipher Bits Not Set.");
11010
0
    }
11011
    /* macStr */
11012
0
    macStr = GetCipherMacStr(n);
11013
11014
11015
    /* Build up the string by copying onto the end. */
11016
0
    XSTRNCPY(dp, name, (size_t)len);
11017
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11018
0
    len -= strLen; dp += strLen;
11019
11020
0
    XSTRNCPY(dp, " ", (size_t)len);
11021
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11022
0
    len -= strLen; dp += strLen;
11023
0
    XSTRNCPY(dp, protocol, (size_t)len);
11024
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11025
0
    len -= strLen; dp += strLen;
11026
11027
0
    XSTRNCPY(dp, " Kx=", (size_t)len);
11028
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11029
0
    len -= strLen; dp += strLen;
11030
0
    XSTRNCPY(dp, keaStr, (size_t)len);
11031
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11032
0
    len -= strLen; dp += strLen;
11033
11034
0
    XSTRNCPY(dp, " Au=", (size_t)len);
11035
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11036
0
    len -= strLen; dp += strLen;
11037
0
    XSTRNCPY(dp, authStr, (size_t)len);
11038
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11039
0
    len -= strLen; dp += strLen;
11040
11041
0
    XSTRNCPY(dp, " Enc=", (size_t)len);
11042
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11043
0
    len -= strLen; dp += strLen;
11044
0
    XSTRNCPY(dp, encStr, (size_t)len);
11045
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11046
0
    len -= strLen; dp += strLen;
11047
11048
0
    XSTRNCPY(dp, " Mac=", (size_t)len);
11049
0
    dp[len-1] = '\0'; strLen = (int)XSTRLEN(dp);
11050
0
    len -= strLen; dp += (size_t)strLen;
11051
0
    XSTRNCPY(dp, macStr, (size_t)len);
11052
0
    dp[len-1] = '\0';
11053
11054
0
    return WOLFSSL_SUCCESS;
11055
0
}
11056
#endif /* OPENSSL_ALL || WOLFSSL_QT */
11057
11058
static WC_INLINE const char* wolfssl_kea_to_string(int kea)
11059
0
{
11060
0
    const char* keaStr;
11061
11062
0
    switch (kea) {
11063
0
        case no_kea:
11064
0
            keaStr = "None";
11065
0
            break;
11066
0
#ifndef NO_RSA
11067
0
        case rsa_kea:
11068
0
            keaStr = "RSA";
11069
0
            break;
11070
0
#endif
11071
0
#ifndef NO_DH
11072
0
        case diffie_hellman_kea:
11073
0
            keaStr = "DHE";
11074
0
            break;
11075
0
#endif
11076
0
        case fortezza_kea:
11077
0
            keaStr = "FZ";
11078
0
            break;
11079
#ifndef NO_PSK
11080
        case psk_kea:
11081
            keaStr = "PSK";
11082
            break;
11083
    #ifndef NO_DH
11084
        case dhe_psk_kea:
11085
            keaStr = "DHEPSK";
11086
            break;
11087
    #endif
11088
    #ifdef HAVE_ECC
11089
        case ecdhe_psk_kea:
11090
            keaStr = "ECDHEPSK";
11091
            break;
11092
    #endif
11093
#endif
11094
0
#ifdef HAVE_ECC
11095
0
        case ecc_diffie_hellman_kea:
11096
0
            keaStr = "ECDHE";
11097
0
            break;
11098
0
        case ecc_static_diffie_hellman_kea:
11099
0
            keaStr = "ECDH";
11100
0
            break;
11101
0
#endif
11102
0
        case any_kea:
11103
0
            keaStr = "any";
11104
0
            break;
11105
0
        default:
11106
0
            keaStr = "unknown";
11107
0
            break;
11108
0
    }
11109
11110
0
    return keaStr;
11111
0
}
11112
11113
static WC_INLINE const char* wolfssl_sigalg_to_string(int sig_algo)
11114
0
{
11115
0
    const char* authStr;
11116
11117
0
    switch (sig_algo) {
11118
0
        case anonymous_sa_algo:
11119
0
            authStr = "None";
11120
0
            break;
11121
0
#ifndef NO_RSA
11122
0
        case rsa_sa_algo:
11123
0
            authStr = "RSA";
11124
0
            break;
11125
0
    #ifdef WC_RSA_PSS
11126
0
        case rsa_pss_sa_algo:
11127
0
            authStr = "RSA-PSS";
11128
0
            break;
11129
0
    #endif
11130
0
#endif
11131
#ifndef NO_DSA
11132
        case dsa_sa_algo:
11133
            authStr = "DSA";
11134
            break;
11135
#endif
11136
0
#ifdef HAVE_ECC
11137
0
        case ecc_dsa_sa_algo:
11138
0
            authStr = "ECDSA";
11139
0
            break;
11140
0
#endif
11141
0
#ifdef WOLFSSL_SM2
11142
0
        case sm2_sa_algo:
11143
0
            authStr = "SM2";
11144
0
            break;
11145
0
#endif
11146
0
#ifdef HAVE_ED25519
11147
0
        case ed25519_sa_algo:
11148
0
            authStr = "Ed25519";
11149
0
            break;
11150
0
#endif
11151
0
#ifdef HAVE_ED448
11152
0
        case ed448_sa_algo:
11153
0
            authStr = "Ed448";
11154
0
            break;
11155
0
#endif
11156
0
        case any_sa_algo:
11157
0
            authStr = "any";
11158
0
            break;
11159
0
        default:
11160
0
            authStr = "unknown";
11161
0
            break;
11162
0
    }
11163
11164
0
    return authStr;
11165
0
}
11166
11167
static WC_INLINE const char* wolfssl_cipher_to_string(int cipher, int key_size)
11168
0
{
11169
0
    const char* encStr;
11170
11171
0
    (void)key_size;
11172
11173
0
    switch (cipher) {
11174
0
        case wolfssl_cipher_null:
11175
0
            encStr = "None";
11176
0
            break;
11177
0
#ifndef NO_RC4
11178
0
        case wolfssl_rc4:
11179
0
            encStr = "RC4(128)";
11180
0
            break;
11181
0
#endif
11182
0
#ifndef NO_DES3
11183
0
        case wolfssl_triple_des:
11184
0
            encStr = "3DES(168)";
11185
0
            break;
11186
0
#endif
11187
0
#ifndef NO_AES
11188
0
        case wolfssl_aes:
11189
0
            if (key_size == AES_128_KEY_SIZE)
11190
0
                encStr = "AES(128)";
11191
0
            else if (key_size == AES_256_KEY_SIZE)
11192
0
                encStr = "AES(256)";
11193
0
            else
11194
0
                encStr = "AES(?)";
11195
0
            break;
11196
0
    #ifdef HAVE_AESGCM
11197
0
        case wolfssl_aes_gcm:
11198
0
            if (key_size == AES_128_KEY_SIZE)
11199
0
                encStr = "AESGCM(128)";
11200
0
            else if (key_size == AES_256_KEY_SIZE)
11201
0
                encStr = "AESGCM(256)";
11202
0
            else
11203
0
                encStr = "AESGCM(?)";
11204
0
            break;
11205
0
    #endif
11206
0
    #ifdef HAVE_AESCCM
11207
0
        case wolfssl_aes_ccm:
11208
0
            if (key_size == AES_128_KEY_SIZE)
11209
0
                encStr = "AESCCM(128)";
11210
0
            else if (key_size == AES_256_KEY_SIZE)
11211
0
                encStr = "AESCCM(256)";
11212
0
            else
11213
0
                encStr = "AESCCM(?)";
11214
0
            break;
11215
0
    #endif
11216
0
#endif
11217
0
#ifdef HAVE_CHACHA
11218
0
        case wolfssl_chacha:
11219
0
            encStr = "CHACHA20/POLY1305(256)";
11220
0
            break;
11221
0
#endif
11222
#ifdef HAVE_ARIA
11223
        case wolfssl_aria_gcm:
11224
            if (key_size == ARIA_128_KEY_SIZE)
11225
                encStr = "Aria(128)";
11226
            else if (key_size == ARIA_192_KEY_SIZE)
11227
                encStr = "Aria(192)";
11228
            else if (key_size == ARIA_256_KEY_SIZE)
11229
                encStr = "Aria(256)";
11230
            else
11231
                encStr = "Aria(?)";
11232
            break;
11233
#endif
11234
0
#ifdef HAVE_CAMELLIA
11235
0
        case wolfssl_camellia:
11236
0
            if (key_size == CAMELLIA_128_KEY_SIZE)
11237
0
                encStr = "Camellia(128)";
11238
0
            else if (key_size == CAMELLIA_256_KEY_SIZE)
11239
0
                encStr = "Camellia(256)";
11240
0
            else
11241
0
                encStr = "Camellia(?)";
11242
0
            break;
11243
0
#endif
11244
0
        default:
11245
0
            encStr = "unknown";
11246
0
            break;
11247
0
    }
11248
11249
0
    return encStr;
11250
0
}
11251
11252
static WC_INLINE const char* wolfssl_mac_to_string(int mac)
11253
0
{
11254
0
    const char* macStr;
11255
11256
0
    switch (mac) {
11257
0
        case no_mac:
11258
0
            macStr = "None";
11259
0
            break;
11260
0
#ifndef NO_MD5
11261
0
        case md5_mac:
11262
0
            macStr = "MD5";
11263
0
            break;
11264
0
#endif
11265
0
#ifndef NO_SHA
11266
0
        case sha_mac:
11267
0
            macStr = "SHA1";
11268
0
            break;
11269
0
#endif
11270
0
#ifdef WOLFSSL_SHA224
11271
0
        case sha224_mac:
11272
0
            macStr = "SHA224";
11273
0
            break;
11274
0
#endif
11275
0
#ifndef NO_SHA256
11276
0
        case sha256_mac:
11277
0
            macStr = "SHA256";
11278
0
            break;
11279
0
#endif
11280
0
#ifdef WOLFSSL_SHA384
11281
0
        case sha384_mac:
11282
0
            macStr = "SHA384";
11283
0
            break;
11284
0
#endif
11285
0
#ifdef WOLFSSL_SHA512
11286
0
        case sha512_mac:
11287
0
            macStr = "SHA512";
11288
0
            break;
11289
0
#endif
11290
0
        default:
11291
0
            macStr = "unknown";
11292
0
            break;
11293
0
    }
11294
11295
0
    return macStr;
11296
0
}
11297
11298
char* wolfSSL_CIPHER_description(const WOLFSSL_CIPHER* cipher, char* in,
11299
                                 int len)
11300
0
{
11301
0
    char *ret = in;
11302
0
    const char *keaStr, *authStr, *encStr, *macStr;
11303
0
    size_t strLen;
11304
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_description");
11305
11306
0
    if (cipher == NULL || in == NULL)
11307
0
        return NULL;
11308
11309
0
#if defined(WOLFSSL_QT) || defined(OPENSSL_ALL)
11310
    /* if cipher is in the stack from wolfSSL_get_ciphers_compat then
11311
     * Return the description based on cipher_names[cipher->offset]
11312
     */
11313
0
    if (cipher->in_stack == TRUE) {
11314
0
        wolfSSL_sk_CIPHER_description((WOLFSSL_CIPHER*)cipher);
11315
0
        XSTRNCPY(in,cipher->description,(size_t)len);
11316
0
        return ret;
11317
0
    }
11318
0
#endif
11319
11320
    /* Get the cipher description based on the SSL session cipher */
11321
0
    keaStr = wolfssl_kea_to_string(cipher->ssl->specs.kea);
11322
0
    authStr = wolfssl_sigalg_to_string(cipher->ssl->specs.sig_algo);
11323
0
    encStr = wolfssl_cipher_to_string(cipher->ssl->specs.bulk_cipher_algorithm,
11324
0
                                      cipher->ssl->specs.key_size);
11325
0
    if (cipher->ssl->specs.cipher_type == aead)
11326
0
        macStr = "AEAD";
11327
0
    else
11328
0
        macStr = wolfssl_mac_to_string(cipher->ssl->specs.mac_algorithm);
11329
11330
    /* Build up the string by copying onto the end. */
11331
0
    XSTRNCPY(in, wolfSSL_CIPHER_get_name(cipher), (size_t)len);
11332
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11333
11334
0
    XSTRNCPY(in, " ", (size_t)len);
11335
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11336
0
    XSTRNCPY(in, wolfSSL_get_version(cipher->ssl), (size_t)len);
11337
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11338
11339
0
    XSTRNCPY(in, " Kx=", (size_t)len);
11340
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11341
0
    XSTRNCPY(in, keaStr, (size_t)len);
11342
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11343
11344
0
    XSTRNCPY(in, " Au=", (size_t)len);
11345
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11346
0
    XSTRNCPY(in, authStr, (size_t)len);
11347
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11348
11349
0
    XSTRNCPY(in, " Enc=", (size_t)len);
11350
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11351
0
    XSTRNCPY(in, encStr, (size_t)len);
11352
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11353
11354
0
    XSTRNCPY(in, " Mac=", (size_t)len);
11355
0
    in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen;
11356
0
    XSTRNCPY(in, macStr, (size_t)len);
11357
0
    in[len-1] = '\0';
11358
11359
0
    return ret;
11360
0
}
11361
11362
int wolfSSL_OCSP_parse_url(const char* url, char** host, char** port,
11363
        char** path, int* ssl)
11364
0
{
11365
0
    const char* u = url;
11366
0
    const char* upath; /* path in u */
11367
0
    const char* uport; /* port in u */
11368
0
    const char* hostEnd;
11369
11370
0
    WOLFSSL_ENTER("OCSP_parse_url");
11371
11372
0
    *host = NULL;
11373
0
    *port = NULL;
11374
0
    *path = NULL;
11375
0
    *ssl = 0;
11376
11377
0
    if (*(u++) != 'h') goto err;
11378
0
    if (*(u++) != 't') goto err;
11379
0
    if (*(u++) != 't') goto err;
11380
0
    if (*(u++) != 'p') goto err;
11381
0
    if (*u == 's') {
11382
0
        *ssl = 1;
11383
0
        u++;
11384
0
        *port = CopyString("443", -1, NULL, DYNAMIC_TYPE_OPENSSL);
11385
0
    }
11386
0
    else if (*u == ':') {
11387
0
        *ssl = 0;
11388
0
        *port = CopyString("80", -1, NULL, DYNAMIC_TYPE_OPENSSL);
11389
0
    }
11390
0
    else
11391
0
        goto err;
11392
0
    if (*port == NULL)
11393
0
        goto err;
11394
0
    if (*(u++) != ':') goto err;
11395
0
    if (*(u++) != '/') goto err;
11396
0
    if (*(u++) != '/') goto err;
11397
11398
    /* Look for path */
11399
0
    upath = XSTRSTR(u, "/");
11400
0
    *path = CopyString(upath == NULL ? "/" : upath, -1, NULL,
11401
0
                       DYNAMIC_TYPE_OPENSSL);
11402
11403
    /* Look for port */
11404
0
    uport = XSTRSTR(u, ":");
11405
0
    if (uport != NULL) {
11406
0
        if (*(++uport) == '\0')
11407
0
            goto err;
11408
        /* port must be before path */
11409
0
        if (upath != NULL && uport >= upath)
11410
0
            goto err;
11411
0
        XFREE(*port, NULL, DYNAMIC_TYPE_OPENSSL);
11412
0
        *port = CopyString(uport, upath != NULL ? (int)(upath - uport) : -1,
11413
0
                           NULL, DYNAMIC_TYPE_OPENSSL);
11414
0
        if (*port == NULL)
11415
0
            goto err;
11416
0
        hostEnd = uport - 1;
11417
0
    }
11418
0
    else
11419
0
        hostEnd = upath;
11420
11421
0
    *host = CopyString(u, hostEnd != NULL ? (int)(hostEnd - u) : -1, NULL,
11422
0
                       DYNAMIC_TYPE_OPENSSL);
11423
0
    if (*host == NULL)
11424
0
        goto err;
11425
11426
0
    return WOLFSSL_SUCCESS;
11427
0
err:
11428
0
    XFREE(*host, NULL, DYNAMIC_TYPE_OPENSSL);
11429
0
    *host = NULL;
11430
0
    XFREE(*port, NULL, DYNAMIC_TYPE_OPENSSL);
11431
0
    *port = NULL;
11432
0
    XFREE(*path, NULL, DYNAMIC_TYPE_OPENSSL);
11433
0
    *path = NULL;
11434
0
    return WOLFSSL_FAILURE;
11435
0
}
11436
11437
#ifndef NO_WOLFSSL_STUB
11438
WOLFSSL_COMP_METHOD* wolfSSL_COMP_zlib(void)
11439
0
{
11440
0
    WOLFSSL_STUB("COMP_zlib");
11441
0
    return 0;
11442
0
}
11443
11444
WOLFSSL_COMP_METHOD* wolfSSL_COMP_rle(void)
11445
0
{
11446
0
    WOLFSSL_STUB("COMP_rle");
11447
0
    return 0;
11448
0
}
11449
11450
int wolfSSL_COMP_add_compression_method(int method, void* data)
11451
0
{
11452
0
    (void)method;
11453
0
    (void)data;
11454
0
    WOLFSSL_STUB("COMP_add_compression_method");
11455
0
    return 0;
11456
0
}
11457
11458
0
const WOLFSSL_COMP_METHOD* wolfSSL_get_current_compression(const WOLFSSL *ssl) {
11459
0
    (void)ssl;
11460
0
    return NULL;
11461
0
}
11462
11463
0
const WOLFSSL_COMP_METHOD* wolfSSL_get_current_expansion(const WOLFSSL *ssl) {
11464
0
    (void)ssl;
11465
0
    return NULL;
11466
0
}
11467
11468
const char* wolfSSL_COMP_get_name(const WOLFSSL_COMP_METHOD *comp)
11469
0
{
11470
0
    static const char ret[] = "not supported";
11471
11472
0
    (void)comp;
11473
0
    WOLFSSL_STUB("wolfSSL_COMP_get_name");
11474
0
    return ret;
11475
0
}
11476
#endif
11477
11478
/*  wolfSSL_set_dynlock_create_callback
11479
 *  CRYPTO_set_dynlock_create_callback has been deprecated since openSSL 1.0.1.
11480
 *  This function exists for compatibility purposes because wolfSSL satisfies
11481
 *  thread safety without relying on the callback.
11482
 */
11483
void wolfSSL_set_dynlock_create_callback(WOLFSSL_dynlock_value* (*f)(
11484
                                                          const char*, int))
11485
0
{
11486
0
    WOLFSSL_STUB("CRYPTO_set_dynlock_create_callback");
11487
0
    (void)f;
11488
0
}
11489
/*  wolfSSL_set_dynlock_lock_callback
11490
 *  CRYPTO_set_dynlock_lock_callback has been deprecated since openSSL 1.0.1.
11491
 *  This function exists for compatibility purposes because wolfSSL satisfies
11492
 *  thread safety without relying on the callback.
11493
 */
11494
void wolfSSL_set_dynlock_lock_callback(
11495
             void (*f)(int, WOLFSSL_dynlock_value*, const char*, int))
11496
0
{
11497
0
    WOLFSSL_STUB("CRYPTO_set_set_dynlock_lock_callback");
11498
0
    (void)f;
11499
0
}
11500
/*  wolfSSL_set_dynlock_destroy_callback
11501
 *  CRYPTO_set_dynlock_destroy_callback has been deprecated since openSSL 1.0.1.
11502
 *  This function exists for compatibility purposes because wolfSSL satisfies
11503
 *  thread safety without relying on the callback.
11504
 */
11505
void wolfSSL_set_dynlock_destroy_callback(
11506
                  void (*f)(WOLFSSL_dynlock_value*, const char*, int))
11507
0
{
11508
0
    WOLFSSL_STUB("CRYPTO_set_set_dynlock_destroy_callback");
11509
0
    (void)f;
11510
0
}
11511
11512
11513
/* Sets the DNS hostname to name.
11514
 * Hostname is cleared if name is NULL or empty. */
11515
int wolfSSL_set1_host(WOLFSSL * ssl, const char* name)
11516
0
{
11517
0
    if (ssl == NULL) {
11518
0
        return WOLFSSL_FAILURE;
11519
0
    }
11520
11521
0
    return wolfSSL_X509_VERIFY_PARAM_set1_host(ssl->param, name, 0);
11522
0
}
11523
11524
/******************************************************************************
11525
* wolfSSL_CTX_set1_param - set a pointer to the SSL verification parameters
11526
*
11527
* RETURNS:
11528
*   WOLFSSL_SUCCESS on success, otherwise returns WOLFSSL_FAILURE
11529
*   Note: Returns WOLFSSL_SUCCESS, in case either parameter is NULL,
11530
*   same as openssl.
11531
*/
11532
int wolfSSL_CTX_set1_param(WOLFSSL_CTX* ctx, WOLFSSL_X509_VERIFY_PARAM *vpm)
11533
0
{
11534
0
    if (ctx == NULL || vpm == NULL)
11535
0
        return WOLFSSL_SUCCESS;
11536
11537
0
    return wolfSSL_X509_VERIFY_PARAM_set1(ctx->param, vpm);
11538
0
}
11539
11540
/******************************************************************************
11541
* wolfSSL_CTX/_get0_param - return a pointer to the SSL verification parameters
11542
*
11543
* RETURNS:
11544
* returns pointer to the SSL verification parameters on success,
11545
* otherwise returns NULL
11546
*/
11547
WOLFSSL_X509_VERIFY_PARAM* wolfSSL_CTX_get0_param(WOLFSSL_CTX* ctx)
11548
81.1k
{
11549
81.1k
    if (ctx == NULL) {
11550
0
        return NULL;
11551
0
    }
11552
11553
81.1k
    return ctx->param;
11554
81.1k
}
11555
11556
WOLFSSL_X509_VERIFY_PARAM* wolfSSL_get0_param(WOLFSSL* ssl)
11557
88.9k
{
11558
88.9k
    if (ssl == NULL) {
11559
0
        return NULL;
11560
0
    }
11561
88.9k
    return ssl->param;
11562
88.9k
}
11563
11564
#endif /* OPENSSL_EXTRA */
11565
11566
#if defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL)
11567
/* Gets an index to store SSL structure at.
11568
 *
11569
 * Returns positive index on success and negative values on failure
11570
 */
11571
int wolfSSL_get_ex_data_X509_STORE_CTX_idx(void)
11572
0
{
11573
0
    WOLFSSL_ENTER("wolfSSL_get_ex_data_X509_STORE_CTX_idx");
11574
11575
    /* store SSL at index 0 */
11576
0
    return 0;
11577
0
}
11578
#endif /* OPENSSL_EXTRA || WOLFSSL_WPAS_SMALL */
11579
11580
#ifdef OPENSSL_EXTRA
11581
/* Sets a function callback that will send information about the state of all
11582
 * WOLFSSL objects that have been created by the WOLFSSL_CTX structure passed
11583
 * in.
11584
 *
11585
 * ctx WOLFSSL_CTX structure to set callback function in
11586
 * f   callback function to use
11587
 */
11588
void wolfSSL_CTX_set_info_callback(WOLFSSL_CTX* ctx,
11589
       void (*f)(const WOLFSSL* ssl, int type, int val))
11590
0
{
11591
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_info_callback");
11592
0
    if (ctx == NULL) {
11593
0
        WOLFSSL_MSG("Bad function argument");
11594
0
    }
11595
0
    else {
11596
0
        ctx->CBIS = f;
11597
0
    }
11598
0
}
11599
11600
void wolfSSL_set_info_callback(WOLFSSL* ssl,
11601
       void (*f)(const WOLFSSL* ssl, int type, int val))
11602
0
{
11603
0
    WOLFSSL_ENTER("wolfSSL_set_info_callback");
11604
0
    if (ssl == NULL) {
11605
0
        WOLFSSL_MSG("Bad function argument");
11606
0
    }
11607
0
    else {
11608
0
        ssl->CBIS = f;
11609
0
    }
11610
0
}
11611
11612
11613
unsigned long wolfSSL_ERR_peek_error(void)
11614
0
{
11615
0
    WOLFSSL_ENTER("wolfSSL_ERR_peek_error");
11616
11617
0
    return wolfSSL_ERR_peek_error_line_data(NULL, NULL, NULL, NULL);
11618
0
}
11619
11620
#ifdef WOLFSSL_DEBUG_TRACE_ERROR_CODES_H
11621
#include <wolfssl/debug-untrace-error-codes.h>
11622
#endif
11623
11624
int wolfSSL_ERR_GET_LIB(unsigned long err)
11625
0
{
11626
0
    unsigned long value;
11627
11628
0
    value = (err & 0xFFFFFFL);
11629
0
    switch (value) {
11630
0
    case -PARSE_ERROR:
11631
0
        return WOLFSSL_ERR_LIB_SSL;
11632
0
    case -ASN_NO_PEM_HEADER:
11633
0
    case -WOLFSSL_PEM_R_NO_START_LINE_E:
11634
0
    case -WOLFSSL_PEM_R_PROBLEMS_GETTING_PASSWORD_E:
11635
0
    case -WOLFSSL_PEM_R_BAD_PASSWORD_READ_E:
11636
0
    case -WOLFSSL_PEM_R_BAD_DECRYPT_E:
11637
0
        return WOLFSSL_ERR_LIB_PEM;
11638
0
    case -WOLFSSL_EVP_R_BAD_DECRYPT_E:
11639
0
    case -WOLFSSL_EVP_R_BN_DECODE_ERROR:
11640
0
    case -WOLFSSL_EVP_R_DECODE_ERROR:
11641
0
    case -WOLFSSL_EVP_R_PRIVATE_KEY_DECODE_ERROR:
11642
0
        return WOLFSSL_ERR_LIB_EVP;
11643
0
    case -WOLFSSL_ASN1_R_HEADER_TOO_LONG_E:
11644
0
        return WOLFSSL_ERR_LIB_ASN1;
11645
0
    default:
11646
0
        return 0;
11647
0
    }
11648
0
}
11649
11650
#ifdef WOLFSSL_DEBUG_TRACE_ERROR_CODES
11651
#include <wolfssl/debug-trace-error-codes.h>
11652
#endif
11653
11654
/* This function is to find global error values that are the same through out
11655
 * all library version. With wolfSSL having only one set of error codes the
11656
 * return value is pretty straight forward. The only thing needed is all wolfSSL
11657
 * error values are typically negative.
11658
 *
11659
 * Returns the error reason
11660
 */
11661
int wolfSSL_ERR_GET_REASON(unsigned long err)
11662
0
{
11663
0
    int ret = (int)err;
11664
11665
0
    WOLFSSL_ENTER("wolfSSL_ERR_GET_REASON");
11666
11667
0
#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY)
11668
    /* Nginx looks for this error to know to stop parsing certificates.
11669
     * Same for HAProxy. */
11670
0
    if (err == ((ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE) ||
11671
0
       ((err & 0xFFFFFFL) == -WC_NO_ERR_TRACE(ASN_NO_PEM_HEADER)) ||
11672
0
       ((err & 0xFFFL) == PEM_R_NO_START_LINE ))
11673
0
        return PEM_R_NO_START_LINE;
11674
0
    if (err == ((ERR_LIB_SSL << 24) | -SSL_R_HTTP_REQUEST))
11675
0
        return SSL_R_HTTP_REQUEST;
11676
0
#endif
11677
#if defined(OPENSSL_ALL) && defined(WOLFSSL_PYTHON)
11678
    if (err == ((ERR_LIB_ASN1 << 24) | ASN1_R_HEADER_TOO_LONG))
11679
        return ASN1_R_HEADER_TOO_LONG;
11680
#endif
11681
11682
    /* check if error value is in range of wolfCrypt or wolfSSL errors */
11683
0
    ret = 0 - ret; /* setting as negative value */
11684
11685
0
    if ((ret <= WC_SPAN1_FIRST_E && ret >= WC_SPAN1_LAST_E) ||
11686
0
        (ret <= WC_SPAN2_FIRST_E && ret >= WC_SPAN2_LAST_E) ||
11687
0
        (ret <= WOLFSSL_FIRST_E && ret >= WOLFSSL_LAST_E))
11688
0
    {
11689
0
        return ret;
11690
0
    }
11691
0
    else {
11692
0
        WOLFSSL_MSG("Not in range of typical error values");
11693
0
        ret = (int)err;
11694
0
    }
11695
11696
0
    return ret;
11697
0
}
11698
11699
#ifndef NO_TLS
11700
/* returns a string that describes the alert
11701
 *
11702
 * alertID the alert value to look up
11703
 */
11704
const char* wolfSSL_alert_type_string_long(int alertID)
11705
0
{
11706
0
    WOLFSSL_ENTER("wolfSSL_alert_type_string_long");
11707
11708
0
    return AlertTypeToString(alertID);
11709
0
}
11710
11711
const char* wolfSSL_alert_desc_string_long(int alertID)
11712
0
{
11713
0
    WOLFSSL_ENTER("wolfSSL_alert_desc_string_long");
11714
11715
0
    return AlertTypeToString(alertID);
11716
0
}
11717
#endif /* !NO_TLS */
11718
11719
#define STATE_STRINGS_PROTO(s) \
11720
0
    {                          \
11721
0
        {"SSLv3 " s,           \
11722
0
         "SSLv3 " s,           \
11723
0
         "SSLv3 " s},          \
11724
0
        {"TLSv1 " s,           \
11725
0
         "TLSv1 " s,           \
11726
0
         "TLSv1 " s},          \
11727
0
        {"TLSv1_1 " s,         \
11728
0
         "TLSv1_1 " s,         \
11729
0
         "TLSv1_1 " s},        \
11730
0
        {"TLSv1_2 " s,         \
11731
0
         "TLSv1_2 " s,         \
11732
0
         "TLSv1_2 " s},        \
11733
0
        {"TLSv1_3 " s,         \
11734
0
         "TLSv1_3 " s,         \
11735
0
         "TLSv1_3 " s},        \
11736
0
        {"DTLSv1 " s,          \
11737
0
         "DTLSv1 " s,          \
11738
0
         "DTLSv1 " s},         \
11739
0
        {"DTLSv1_2 " s,        \
11740
0
         "DTLSv1_2 " s,        \
11741
0
         "DTLSv1_2 " s},       \
11742
0
        {"DTLSv1_3 " s,        \
11743
0
         "DTLSv1_3 " s,        \
11744
0
         "DTLSv1_3 " s},       \
11745
0
    }
11746
11747
#define STATE_STRINGS_PROTO_RW(s) \
11748
0
    {                             \
11749
0
        {"SSLv3 read " s,         \
11750
0
         "SSLv3 write " s,        \
11751
0
         "SSLv3 " s},             \
11752
0
        {"TLSv1 read " s,         \
11753
0
         "TLSv1 write " s,        \
11754
0
         "TLSv1 " s},             \
11755
0
        {"TLSv1_1 read " s,       \
11756
0
         "TLSv1_1 write " s,      \
11757
0
         "TLSv1_1 " s},           \
11758
0
        {"TLSv1_2 read " s,       \
11759
0
         "TLSv1_2 write " s,      \
11760
0
         "TLSv1_2 " s},           \
11761
0
        {"TLSv1_3 read " s,       \
11762
0
         "TLSv1_3 write " s,      \
11763
0
         "TLSv1_3 " s},           \
11764
0
        {"DTLSv1 read " s,        \
11765
0
         "DTLSv1 write " s,       \
11766
0
         "DTLSv1 " s},            \
11767
0
        {"DTLSv1_2 read " s,      \
11768
0
         "DTLSv1_2 write " s,     \
11769
0
         "DTLSv1_2 " s},          \
11770
0
        {"DTLSv1_3 read " s,      \
11771
0
         "DTLSv1_3 write " s,     \
11772
0
         "DTLSv1_3 " s},          \
11773
0
    }
11774
11775
/* Gets the current state of the WOLFSSL structure
11776
 *
11777
 * ssl WOLFSSL structure to get state of
11778
 *
11779
 * Returns a human readable string of the WOLFSSL structure state
11780
 */
11781
const char* wolfSSL_state_string_long(const WOLFSSL* ssl)
11782
0
{
11783
11784
0
    static const char* OUTPUT_STR[24][8][3] = {
11785
0
        STATE_STRINGS_PROTO("Initialization"),
11786
0
        STATE_STRINGS_PROTO_RW("Server Hello Request"),
11787
0
        STATE_STRINGS_PROTO_RW("Server Hello Verify Request"),
11788
0
        STATE_STRINGS_PROTO_RW("Server Hello Retry Request"),
11789
0
        STATE_STRINGS_PROTO_RW("Server Hello"),
11790
0
        STATE_STRINGS_PROTO_RW("Server Certificate Status"),
11791
0
        STATE_STRINGS_PROTO_RW("Server Encrypted Extensions"),
11792
0
        STATE_STRINGS_PROTO_RW("Server Session Ticket"),
11793
0
        STATE_STRINGS_PROTO_RW("Server Certificate Request"),
11794
0
        STATE_STRINGS_PROTO_RW("Server Cert"),
11795
0
        STATE_STRINGS_PROTO_RW("Server Key Exchange"),
11796
0
        STATE_STRINGS_PROTO_RW("Server Hello Done"),
11797
0
        STATE_STRINGS_PROTO_RW("Server Change CipherSpec"),
11798
0
        STATE_STRINGS_PROTO_RW("Server Finished"),
11799
0
        STATE_STRINGS_PROTO_RW("server Key Update"),
11800
0
        STATE_STRINGS_PROTO_RW("Client Hello"),
11801
0
        STATE_STRINGS_PROTO_RW("Client Key Exchange"),
11802
0
        STATE_STRINGS_PROTO_RW("Client Cert"),
11803
0
        STATE_STRINGS_PROTO_RW("Client Change CipherSpec"),
11804
0
        STATE_STRINGS_PROTO_RW("Client Certificate Verify"),
11805
0
        STATE_STRINGS_PROTO_RW("Client End Of Early Data"),
11806
0
        STATE_STRINGS_PROTO_RW("Client Finished"),
11807
0
        STATE_STRINGS_PROTO_RW("Client Key Update"),
11808
0
        STATE_STRINGS_PROTO("Handshake Done"),
11809
0
    };
11810
0
    enum ProtocolVer {
11811
0
        SSL_V3 = 0,
11812
0
        TLS_V1,
11813
0
        TLS_V1_1,
11814
0
        TLS_V1_2,
11815
0
        TLS_V1_3,
11816
0
        DTLS_V1,
11817
0
        DTLS_V1_2,
11818
0
        DTLS_V1_3,
11819
0
        UNKNOWN = 100
11820
0
    };
11821
11822
0
    enum IOMode {
11823
0
        SS_READ = 0,
11824
0
        SS_WRITE,
11825
0
        SS_NEITHER
11826
0
    };
11827
11828
0
    enum SslState {
11829
0
        ss_null_state = 0,
11830
0
        ss_server_hellorequest,
11831
0
        ss_server_helloverify,
11832
0
        ss_server_helloretryrequest,
11833
0
        ss_server_hello,
11834
0
        ss_server_certificatestatus,
11835
0
        ss_server_encryptedextensions,
11836
0
        ss_server_sessionticket,
11837
0
        ss_server_certrequest,
11838
0
        ss_server_cert,
11839
0
        ss_server_keyexchange,
11840
0
        ss_server_hellodone,
11841
0
        ss_server_changecipherspec,
11842
0
        ss_server_finished,
11843
0
        ss_server_keyupdate,
11844
0
        ss_client_hello,
11845
0
        ss_client_keyexchange,
11846
0
        ss_client_cert,
11847
0
        ss_client_changecipherspec,
11848
0
        ss_client_certverify,
11849
0
        ss_client_endofearlydata,
11850
0
        ss_client_finished,
11851
0
        ss_client_keyupdate,
11852
0
        ss_handshake_done
11853
0
    };
11854
11855
0
    int protocol = 0;
11856
0
    int cbmode = 0;
11857
0
    int state = 0;
11858
11859
0
    WOLFSSL_ENTER("wolfSSL_state_string_long");
11860
0
    if (ssl == NULL) {
11861
0
        WOLFSSL_MSG("Null argument passed in");
11862
0
        return NULL;
11863
0
    }
11864
11865
    /* Get state of callback */
11866
0
    if (ssl->cbmode == WOLFSSL_CB_MODE_WRITE) {
11867
0
        cbmode =  SS_WRITE;
11868
0
    }
11869
0
    else if (ssl->cbmode == WOLFSSL_CB_MODE_READ) {
11870
0
        cbmode =  SS_READ;
11871
0
    }
11872
0
    else {
11873
0
        cbmode =  SS_NEITHER;
11874
0
    }
11875
11876
    /* Get protocol version */
11877
0
    switch (ssl->version.major) {
11878
0
        case SSLv3_MAJOR:
11879
0
            switch (ssl->version.minor) {
11880
0
                case SSLv3_MINOR:
11881
0
                    protocol = SSL_V3;
11882
0
                    break;
11883
0
                case TLSv1_MINOR:
11884
0
                    protocol = TLS_V1;
11885
0
                    break;
11886
0
                case TLSv1_1_MINOR:
11887
0
                    protocol = TLS_V1_1;
11888
0
                    break;
11889
0
                case TLSv1_2_MINOR:
11890
0
                    protocol = TLS_V1_2;
11891
0
                    break;
11892
0
                case TLSv1_3_MINOR:
11893
0
                    protocol = TLS_V1_3;
11894
0
                    break;
11895
0
                default:
11896
0
                    protocol = UNKNOWN;
11897
0
            }
11898
0
            break;
11899
0
        case DTLS_MAJOR:
11900
0
            switch (ssl->version.minor) {
11901
0
                case DTLS_MINOR:
11902
0
                    protocol = DTLS_V1;
11903
0
                    break;
11904
0
                case DTLSv1_2_MINOR:
11905
0
                    protocol = DTLS_V1_2;
11906
0
                    break;
11907
0
                case DTLSv1_3_MINOR:
11908
0
                    protocol = DTLS_V1_3;
11909
0
                    break;
11910
0
                default:
11911
0
                    protocol = UNKNOWN;
11912
0
            }
11913
0
            break;
11914
0
    default:
11915
0
        protocol = UNKNOWN;
11916
0
    }
11917
11918
    /* accept process */
11919
0
    if (ssl->cbmode == WOLFSSL_CB_MODE_READ) {
11920
0
        state = ssl->cbtype;
11921
0
        switch (state) {
11922
0
            case hello_request:
11923
0
                state = ss_server_hellorequest;
11924
0
                break;
11925
0
            case client_hello:
11926
0
                state = ss_client_hello;
11927
0
                break;
11928
0
            case server_hello:
11929
0
                state = ss_server_hello;
11930
0
                break;
11931
0
            case hello_verify_request:
11932
0
                state = ss_server_helloverify;
11933
0
                break;
11934
0
            case session_ticket:
11935
0
                state = ss_server_sessionticket;
11936
0
                break;
11937
0
            case end_of_early_data:
11938
0
                state = ss_client_endofearlydata;
11939
0
                break;
11940
0
            case hello_retry_request:
11941
0
                state = ss_server_helloretryrequest;
11942
0
                break;
11943
0
            case encrypted_extensions:
11944
0
                state = ss_server_encryptedextensions;
11945
0
                break;
11946
0
            case certificate:
11947
0
                if (ssl->options.side == WOLFSSL_SERVER_END)
11948
0
                    state = ss_client_cert;
11949
0
                else if (ssl->options.side == WOLFSSL_CLIENT_END)
11950
0
                    state = ss_server_cert;
11951
0
                else {
11952
0
                    WOLFSSL_MSG("Unknown State");
11953
0
                    state = ss_null_state;
11954
0
                }
11955
0
                break;
11956
0
            case server_key_exchange:
11957
0
                state = ss_server_keyexchange;
11958
0
                break;
11959
0
            case certificate_request:
11960
0
                state = ss_server_certrequest;
11961
0
                break;
11962
0
            case server_hello_done:
11963
0
                state = ss_server_hellodone;
11964
0
                break;
11965
0
            case certificate_verify:
11966
0
                state = ss_client_certverify;
11967
0
                break;
11968
0
            case client_key_exchange:
11969
0
                state = ss_client_keyexchange;
11970
0
                break;
11971
0
            case finished:
11972
0
                if (ssl->options.side == WOLFSSL_SERVER_END)
11973
0
                    state = ss_client_finished;
11974
0
                else if (ssl->options.side == WOLFSSL_CLIENT_END)
11975
0
                    state = ss_server_finished;
11976
0
                else {
11977
0
                    WOLFSSL_MSG("Unknown State");
11978
0
                    state = ss_null_state;
11979
0
                }
11980
0
                break;
11981
0
            case certificate_status:
11982
0
                state = ss_server_certificatestatus;
11983
0
                break;
11984
0
            case key_update:
11985
0
                if (ssl->options.side == WOLFSSL_SERVER_END)
11986
0
                    state = ss_client_keyupdate;
11987
0
                else if (ssl->options.side == WOLFSSL_CLIENT_END)
11988
0
                    state = ss_server_keyupdate;
11989
0
                else {
11990
0
                    WOLFSSL_MSG("Unknown State");
11991
0
                    state = ss_null_state;
11992
0
                }
11993
0
                break;
11994
0
            case change_cipher_hs:
11995
0
                if (ssl->options.side == WOLFSSL_SERVER_END)
11996
0
                    state = ss_client_changecipherspec;
11997
0
                else if (ssl->options.side == WOLFSSL_CLIENT_END)
11998
0
                    state = ss_server_changecipherspec;
11999
0
                else {
12000
0
                    WOLFSSL_MSG("Unknown State");
12001
0
                    state = ss_null_state;
12002
0
                }
12003
0
                break;
12004
0
            default:
12005
0
                WOLFSSL_MSG("Unknown State");
12006
0
                state = ss_null_state;
12007
0
        }
12008
0
    }
12009
0
    else {
12010
        /* Send process */
12011
0
        if (ssl->options.side == WOLFSSL_SERVER_END)
12012
0
            state = ssl->options.serverState;
12013
0
        else
12014
0
            state = ssl->options.clientState;
12015
12016
0
        switch (state) {
12017
0
            case SERVER_HELLOVERIFYREQUEST_COMPLETE:
12018
0
                state = ss_server_helloverify;
12019
0
                break;
12020
0
            case SERVER_HELLO_RETRY_REQUEST_COMPLETE:
12021
0
                state = ss_server_helloretryrequest;
12022
0
                break;
12023
0
            case SERVER_HELLO_COMPLETE:
12024
0
                state = ss_server_hello;
12025
0
                break;
12026
0
            case SERVER_ENCRYPTED_EXTENSIONS_COMPLETE:
12027
0
                state = ss_server_encryptedextensions;
12028
0
                break;
12029
0
            case SERVER_CERT_COMPLETE:
12030
0
                state = ss_server_cert;
12031
0
                break;
12032
0
            case SERVER_KEYEXCHANGE_COMPLETE:
12033
0
                state = ss_server_keyexchange;
12034
0
                break;
12035
0
            case SERVER_HELLODONE_COMPLETE:
12036
0
                state = ss_server_hellodone;
12037
0
                break;
12038
0
            case SERVER_CHANGECIPHERSPEC_COMPLETE:
12039
0
                state = ss_server_changecipherspec;
12040
0
                break;
12041
0
            case SERVER_FINISHED_COMPLETE:
12042
0
                state = ss_server_finished;
12043
0
                break;
12044
0
            case CLIENT_HELLO_RETRY:
12045
0
            case CLIENT_HELLO_COMPLETE:
12046
0
                state = ss_client_hello;
12047
0
                break;
12048
0
            case CLIENT_KEYEXCHANGE_COMPLETE:
12049
0
                state = ss_client_keyexchange;
12050
0
                break;
12051
0
            case CLIENT_CHANGECIPHERSPEC_COMPLETE:
12052
0
                state = ss_client_changecipherspec;
12053
0
                break;
12054
0
            case CLIENT_FINISHED_COMPLETE:
12055
0
                state = ss_client_finished;
12056
0
                break;
12057
0
            case HANDSHAKE_DONE:
12058
0
                state = ss_handshake_done;
12059
0
                break;
12060
0
            default:
12061
0
                WOLFSSL_MSG("Unknown State");
12062
0
                state = ss_null_state;
12063
0
        }
12064
0
    }
12065
12066
0
    if (protocol == UNKNOWN) {
12067
0
        WOLFSSL_MSG("Unknown protocol");
12068
0
        return "";
12069
0
    }
12070
0
    else {
12071
0
        return OUTPUT_STR[state][protocol][cbmode];
12072
0
    }
12073
0
}
12074
12075
#endif /* OPENSSL_EXTRA */
12076
12077
static long wolf_set_options(long old_op, long op)
12078
0
{
12079
    /* if SSL_OP_ALL then turn all bug workarounds on */
12080
0
    if ((op & WOLFSSL_OP_ALL) == WOLFSSL_OP_ALL) {
12081
0
        WOLFSSL_MSG("\tSSL_OP_ALL");
12082
0
    }
12083
12084
    /* by default cookie exchange is on with DTLS */
12085
0
    if ((op & WOLFSSL_OP_COOKIE_EXCHANGE) == WOLFSSL_OP_COOKIE_EXCHANGE) {
12086
0
        WOLFSSL_MSG("\tSSL_OP_COOKIE_EXCHANGE : on by default");
12087
0
    }
12088
12089
0
    if ((op & WOLFSSL_OP_NO_SSLv2) == WOLFSSL_OP_NO_SSLv2) {
12090
0
        WOLFSSL_MSG("\tWOLFSSL_OP_NO_SSLv2 : wolfSSL does not support SSLv2");
12091
0
    }
12092
12093
0
#ifdef SSL_OP_NO_TLSv1_3
12094
0
    if ((op & WOLFSSL_OP_NO_TLSv1_3) == WOLFSSL_OP_NO_TLSv1_3) {
12095
0
        WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_3");
12096
0
    }
12097
0
#endif
12098
12099
0
    if ((op & WOLFSSL_OP_NO_TLSv1_2) == WOLFSSL_OP_NO_TLSv1_2) {
12100
0
        WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_2");
12101
0
    }
12102
12103
0
    if ((op & WOLFSSL_OP_NO_TLSv1_1) == WOLFSSL_OP_NO_TLSv1_1) {
12104
0
        WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_1");
12105
0
    }
12106
12107
0
    if ((op & WOLFSSL_OP_NO_TLSv1) == WOLFSSL_OP_NO_TLSv1) {
12108
0
        WOLFSSL_MSG("\tSSL_OP_NO_TLSv1");
12109
0
    }
12110
12111
0
    if ((op & WOLFSSL_OP_NO_SSLv3) == WOLFSSL_OP_NO_SSLv3) {
12112
0
        WOLFSSL_MSG("\tSSL_OP_NO_SSLv3");
12113
0
    }
12114
12115
0
    if ((op & WOLFSSL_OP_CIPHER_SERVER_PREFERENCE) ==
12116
0
            WOLFSSL_OP_CIPHER_SERVER_PREFERENCE) {
12117
0
        WOLFSSL_MSG("\tWOLFSSL_OP_CIPHER_SERVER_PREFERENCE");
12118
0
    }
12119
12120
0
    if ((op & WOLFSSL_OP_NO_COMPRESSION) == WOLFSSL_OP_NO_COMPRESSION) {
12121
    #ifdef HAVE_LIBZ
12122
        WOLFSSL_MSG("SSL_OP_NO_COMPRESSION");
12123
    #else
12124
0
        WOLFSSL_MSG("SSL_OP_NO_COMPRESSION: compression not compiled in");
12125
0
    #endif
12126
0
    }
12127
12128
0
    return old_op | op;
12129
0
}
12130
12131
static int FindHashSig(const Suites* suites, byte first, byte second)
12132
0
{
12133
0
    word16 i;
12134
12135
0
    if (suites == NULL || suites->hashSigAlgoSz == 0) {
12136
0
        WOLFSSL_MSG("Suites pointer error or suiteSz 0");
12137
0
        return SUITES_ERROR;
12138
0
    }
12139
12140
0
    for (i = 0; i < suites->hashSigAlgoSz-1; i += 2) {
12141
0
        if (suites->hashSigAlgo[i]   == first &&
12142
0
            suites->hashSigAlgo[i+1] == second )
12143
0
            return i;
12144
0
    }
12145
12146
0
    return MATCH_SUITE_ERROR;
12147
0
}
12148
12149
long wolfSSL_set_options(WOLFSSL* ssl, long op)
12150
0
{
12151
0
    word16 haveRSA = 1;
12152
0
    word16 havePSK = 0;
12153
0
    int    keySz   = 0;
12154
12155
0
    WOLFSSL_ENTER("wolfSSL_set_options");
12156
12157
0
    if (ssl == NULL) {
12158
0
        return 0;
12159
0
    }
12160
12161
0
    ssl->options.mask = (unsigned long)wolf_set_options((long)ssl->options.mask, op);
12162
12163
0
    if ((ssl->options.mask & WOLFSSL_OP_NO_TLSv1_3) == WOLFSSL_OP_NO_TLSv1_3) {
12164
0
        WOLFSSL_MSG("Disabling TLS 1.3");
12165
0
        if (ssl->version.minor == TLSv1_3_MINOR)
12166
0
            ssl->version.minor = TLSv1_2_MINOR;
12167
0
    }
12168
12169
0
    if ((ssl->options.mask & WOLFSSL_OP_NO_TLSv1_2) == WOLFSSL_OP_NO_TLSv1_2) {
12170
0
        WOLFSSL_MSG("Disabling TLS 1.2");
12171
0
        if (ssl->version.minor == TLSv1_2_MINOR)
12172
0
            ssl->version.minor = TLSv1_1_MINOR;
12173
0
    }
12174
12175
0
    if ((ssl->options.mask & WOLFSSL_OP_NO_TLSv1_1) == WOLFSSL_OP_NO_TLSv1_1) {
12176
0
        WOLFSSL_MSG("Disabling TLS 1.1");
12177
0
        if (ssl->version.minor == TLSv1_1_MINOR)
12178
0
            ssl->version.minor = TLSv1_MINOR;
12179
0
    }
12180
12181
0
    if ((ssl->options.mask & WOLFSSL_OP_NO_TLSv1) == WOLFSSL_OP_NO_TLSv1) {
12182
0
        WOLFSSL_MSG("Disabling TLS 1.0");
12183
0
        if (ssl->version.minor == TLSv1_MINOR)
12184
0
            ssl->version.minor = SSLv3_MINOR;
12185
0
    }
12186
12187
0
    if ((ssl->options.mask & WOLFSSL_OP_NO_COMPRESSION)
12188
0
        == WOLFSSL_OP_NO_COMPRESSION) {
12189
    #ifdef HAVE_LIBZ
12190
        ssl->options.usingCompression = 0;
12191
    #endif
12192
0
    }
12193
12194
0
#if defined(HAVE_SESSION_TICKET) && (defined(OPENSSL_EXTRA) \
12195
0
        || defined(HAVE_WEBSERVER) || defined(WOLFSSL_WPAS_SMALL))
12196
0
    if ((ssl->options.mask & WOLFSSL_OP_NO_TICKET) == WOLFSSL_OP_NO_TICKET) {
12197
0
      ssl->options.noTicketTls12 = 1;
12198
0
    }
12199
0
#endif
12200
12201
12202
    /* in the case of a version change the cipher suites should be reset */
12203
#ifndef NO_PSK
12204
    havePSK = ssl->options.havePSK;
12205
#endif
12206
#ifdef NO_RSA
12207
    haveRSA = 0;
12208
#endif
12209
0
#ifndef NO_CERTS
12210
0
    keySz = ssl->buffers.keySz;
12211
0
#endif
12212
12213
0
    if (ssl->options.side != WOLFSSL_NEITHER_END) {
12214
0
        if (AllocateSuites(ssl) != 0)
12215
0
            return 0;
12216
0
        if (!ssl->suites->setSuites) {
12217
            /* Client side won't set DH params, so it needs haveDH set to TRUE. */
12218
0
            if (ssl->options.side == WOLFSSL_CLIENT_END)
12219
0
                InitSuites(ssl->suites, ssl->version, keySz, haveRSA,
12220
0
                       havePSK, TRUE, ssl->options.haveECDSAsig,
12221
0
                       ssl->options.haveECC, TRUE, ssl->options.haveStaticECC,
12222
0
                       ssl->options.useAnon,
12223
0
                       TRUE, TRUE, TRUE, TRUE, ssl->options.side);
12224
0
            else
12225
0
                InitSuites(ssl->suites, ssl->version, keySz, haveRSA,
12226
0
                       havePSK, ssl->options.haveDH, ssl->options.haveECDSAsig,
12227
0
                       ssl->options.haveECC, TRUE, ssl->options.haveStaticECC,
12228
0
                       ssl->options.useAnon,
12229
0
                       TRUE, TRUE, TRUE, TRUE, ssl->options.side);
12230
0
        }
12231
0
        else {
12232
            /* Only preserve overlapping suites */
12233
0
            Suites tmpSuites;
12234
0
            word16 in, out;
12235
0
            word16 haveECDSAsig, haveStaticECC;
12236
#ifdef NO_RSA
12237
            haveECDSAsig = 1;
12238
            haveStaticECC = 1;
12239
#else
12240
0
            haveECDSAsig = 0;
12241
0
            haveStaticECC = ssl->options.haveStaticECC;
12242
0
#endif
12243
0
            XMEMSET(&tmpSuites, 0, sizeof(Suites));
12244
            /* Get all possible ciphers and sigalgs for the version. Following
12245
             * options limit the allowed ciphers so let's try to get as many as
12246
             * possible.
12247
             * - haveStaticECC turns off haveRSA
12248
             * - haveECDSAsig turns off haveRSAsig */
12249
0
            InitSuites(&tmpSuites, ssl->version, 0, 1, 1, 1, haveECDSAsig, 1, 1,
12250
0
                    haveStaticECC, 1, 1, 1, 1, 1, ssl->options.side);
12251
0
            for (in = 0, out = 0; in < ssl->suites->suiteSz; in += SUITE_LEN) {
12252
0
                if (FindSuite(&tmpSuites, ssl->suites->suites[in],
12253
0
                        ssl->suites->suites[in+1]) >= 0) {
12254
0
                    ssl->suites->suites[out] = ssl->suites->suites[in];
12255
0
                    ssl->suites->suites[out+1] = ssl->suites->suites[in+1];
12256
0
                    out += SUITE_LEN;
12257
0
                }
12258
0
            }
12259
0
            ssl->suites->suiteSz = out;
12260
0
            for (in = 0, out = 0; in < ssl->suites->hashSigAlgoSz; in += 2) {
12261
0
                if (FindHashSig(&tmpSuites, ssl->suites->hashSigAlgo[in],
12262
0
                    ssl->suites->hashSigAlgo[in+1]) >= 0) {
12263
0
                    ssl->suites->hashSigAlgo[out] =
12264
0
                            ssl->suites->hashSigAlgo[in];
12265
0
                    ssl->suites->hashSigAlgo[out+1] =
12266
0
                            ssl->suites->hashSigAlgo[in+1];
12267
0
                    out += 2;
12268
0
                }
12269
0
            }
12270
0
            ssl->suites->hashSigAlgoSz = out;
12271
0
        }
12272
0
    }
12273
12274
0
    return (long)ssl->options.mask;
12275
0
}
12276
12277
12278
long wolfSSL_get_options(const WOLFSSL* ssl)
12279
52.2k
{
12280
52.2k
    WOLFSSL_ENTER("wolfSSL_get_options");
12281
52.2k
    if(ssl == NULL)
12282
0
        return WOLFSSL_FAILURE;
12283
52.2k
    return (long)ssl->options.mask;
12284
52.2k
}
12285
12286
#if defined(HAVE_SECURE_RENEGOTIATION) \
12287
        || defined(HAVE_SERVER_RENEGOTIATION_INFO)
12288
/* clears the counter for number of renegotiations done
12289
 * returns the current count before it is cleared */
12290
long wolfSSL_clear_num_renegotiations(WOLFSSL *s)
12291
0
{
12292
0
    long total;
12293
12294
0
    WOLFSSL_ENTER("wolfSSL_clear_num_renegotiations");
12295
0
    if (s == NULL)
12296
0
        return 0;
12297
12298
0
    total = s->secure_rene_count;
12299
0
    s->secure_rene_count = 0;
12300
0
    return total;
12301
0
}
12302
12303
12304
/* return the number of renegotiations since wolfSSL_new */
12305
long wolfSSL_total_renegotiations(WOLFSSL *s)
12306
0
{
12307
0
    WOLFSSL_ENTER("wolfSSL_total_renegotiations");
12308
0
    return wolfSSL_num_renegotiations(s);
12309
0
}
12310
12311
12312
/* return the number of renegotiations since wolfSSL_new */
12313
long wolfSSL_num_renegotiations(WOLFSSL* s)
12314
0
{
12315
0
    if (s == NULL) {
12316
0
        return 0;
12317
0
    }
12318
12319
0
    return s->secure_rene_count;
12320
0
}
12321
12322
12323
/* Is there a renegotiation currently in progress? */
12324
int  wolfSSL_SSL_renegotiate_pending(WOLFSSL *s)
12325
0
{
12326
0
    return s && s->options.handShakeDone &&
12327
0
            s->options.handShakeState != HANDSHAKE_DONE ? 1 : 0;
12328
0
}
12329
#endif /* HAVE_SECURE_RENEGOTIATION || HAVE_SERVER_RENEGOTIATION_INFO */
12330
12331
#ifdef OPENSSL_EXTRA
12332
12333
long wolfSSL_clear_options(WOLFSSL* ssl, long opt)
12334
0
{
12335
0
    WOLFSSL_ENTER("wolfSSL_clear_options");
12336
0
    if(ssl == NULL)
12337
0
        return WOLFSSL_FAILURE;
12338
0
    ssl->options.mask &= (unsigned long)~opt;
12339
0
    return (long)ssl->options.mask;
12340
0
}
12341
12342
#ifdef HAVE_PK_CALLBACKS
12343
long wolfSSL_set_tlsext_debug_arg(WOLFSSL* ssl, void *arg)
12344
{
12345
    if (ssl == NULL) {
12346
        return WOLFSSL_FAILURE;
12347
    }
12348
12349
    ssl->loggingCtx = arg;
12350
    return WOLFSSL_SUCCESS;
12351
}
12352
#endif /* HAVE_PK_CALLBACKS */
12353
12354
#ifndef NO_WOLFSSL_STUB
12355
long wolfSSL_get_tlsext_status_exts(WOLFSSL *s, void *arg)
12356
0
{
12357
0
    (void)s;
12358
0
    (void)arg;
12359
0
    WOLFSSL_STUB("wolfSSL_get_tlsext_status_exts");
12360
0
    return WOLFSSL_FAILURE;
12361
0
}
12362
#endif
12363
12364
/*** TBD ***/
12365
#ifndef NO_WOLFSSL_STUB
12366
long wolfSSL_set_tlsext_status_exts(WOLFSSL *s, void *arg)
12367
0
{
12368
0
    (void)s;
12369
0
    (void)arg;
12370
0
    WOLFSSL_STUB("wolfSSL_set_tlsext_status_exts");
12371
0
    return WOLFSSL_FAILURE;
12372
0
}
12373
#endif
12374
12375
/*** TBD ***/
12376
#ifndef NO_WOLFSSL_STUB
12377
long wolfSSL_get_tlsext_status_ids(WOLFSSL *s, void *arg)
12378
0
{
12379
0
    (void)s;
12380
0
    (void)arg;
12381
0
    WOLFSSL_STUB("wolfSSL_get_tlsext_status_ids");
12382
0
    return WOLFSSL_FAILURE;
12383
0
}
12384
#endif
12385
12386
/*** TBD ***/
12387
#ifndef NO_WOLFSSL_STUB
12388
long wolfSSL_set_tlsext_status_ids(WOLFSSL *s, void *arg)
12389
0
{
12390
0
    (void)s;
12391
0
    (void)arg;
12392
0
    WOLFSSL_STUB("wolfSSL_set_tlsext_status_ids");
12393
0
    return WOLFSSL_FAILURE;
12394
0
}
12395
#endif
12396
12397
#ifndef NO_WOLFSSL_STUB
12398
/*** TBD ***/
12399
WOLFSSL_EVP_PKEY *wolfSSL_get_privatekey(const WOLFSSL *ssl)
12400
0
{
12401
0
    (void)ssl;
12402
0
    WOLFSSL_STUB("SSL_get_privatekey");
12403
0
    return NULL;
12404
0
}
12405
#endif
12406
12407
#ifndef NO_WOLFSSL_STUB
12408
/*** TBD ***/
12409
void WOLFSSL_CTX_set_tmp_dh_callback(WOLFSSL_CTX *ctx,
12410
    WOLFSSL_DH *(*dh) (WOLFSSL *ssl, int is_export, int keylength))
12411
0
{
12412
0
    (void)ctx;
12413
0
    (void)dh;
12414
0
    WOLFSSL_STUB("WOLFSSL_CTX_set_tmp_dh_callback");
12415
0
}
12416
#endif
12417
12418
#ifndef NO_WOLFSSL_STUB
12419
/*** TBD ***/
12420
WOLF_STACK_OF(WOLFSSL_COMP) *WOLFSSL_COMP_get_compression_methods(void)
12421
0
{
12422
0
    WOLFSSL_STUB("WOLFSSL_COMP_get_compression_methods");
12423
0
    return NULL;
12424
0
}
12425
#endif
12426
12427
12428
#if !defined(NETOS)
12429
void wolfSSL_ERR_load_SSL_strings(void)
12430
0
{
12431
12432
0
}
12433
#endif
12434
12435
#ifdef HAVE_MAX_FRAGMENT
12436
#if !defined(NO_WOLFSSL_CLIENT) && !defined(NO_TLS)
12437
/**
12438
 * Set max fragment tls extension
12439
 * @param c a pointer to WOLFSSL_CTX object
12440
 * @param mode maximum fragment length mode
12441
 * @return 1 on success, otherwise 0 or negative error code
12442
 */
12443
int wolfSSL_CTX_set_tlsext_max_fragment_length(WOLFSSL_CTX *c,
12444
                                               unsigned char mode)
12445
{
12446
    if (c == NULL || (mode < WOLFSSL_MFL_2_9 || mode > WOLFSSL_MFL_2_12 ))
12447
        return BAD_FUNC_ARG;
12448
12449
    return wolfSSL_CTX_UseMaxFragment(c, mode);
12450
}
12451
/**
12452
 * Set max fragment tls extension
12453
 * @param c a pointer to WOLFSSL object
12454
 * @param mode maximum fragment length mode
12455
 * @return 1 on success, otherwise 0 or negative error code
12456
 */
12457
int wolfSSL_set_tlsext_max_fragment_length(WOLFSSL *s, unsigned char mode)
12458
{
12459
    if (s == NULL || (mode < WOLFSSL_MFL_2_9 || mode > WOLFSSL_MFL_2_12 ))
12460
        return BAD_FUNC_ARG;
12461
12462
    return wolfSSL_UseMaxFragment(s, mode);
12463
}
12464
#endif /* !NO_WOLFSSL_CLIENT && !NO_TLS */
12465
#endif /* HAVE_MAX_FRAGMENT */
12466
12467
#endif /* OPENSSL_EXTRA */
12468
12469
#ifdef WOLFSSL_HAVE_TLS_UNIQUE
12470
size_t wolfSSL_get_finished(const WOLFSSL *ssl, void *buf, size_t count)
12471
0
{
12472
0
    byte len = 0;
12473
12474
0
    WOLFSSL_ENTER("wolfSSL_get_finished");
12475
12476
0
    if (!ssl || !buf || count < TLS_FINISHED_SZ) {
12477
0
        WOLFSSL_MSG("Bad parameter");
12478
0
        return WOLFSSL_FAILURE;
12479
0
    }
12480
12481
0
    if (ssl->options.side == WOLFSSL_SERVER_END) {
12482
0
        len = ssl->serverFinished_len;
12483
0
        XMEMCPY(buf, ssl->serverFinished, len);
12484
0
    }
12485
0
    else {
12486
0
        len = ssl->clientFinished_len;
12487
0
        XMEMCPY(buf, ssl->clientFinished, len);
12488
0
    }
12489
0
    return len;
12490
0
}
12491
12492
size_t wolfSSL_get_peer_finished(const WOLFSSL *ssl, void *buf, size_t count)
12493
0
{
12494
0
    byte len = 0;
12495
0
    WOLFSSL_ENTER("wolfSSL_get_peer_finished");
12496
12497
0
    if (!ssl || !buf || count < TLS_FINISHED_SZ) {
12498
0
        WOLFSSL_MSG("Bad parameter");
12499
0
        return WOLFSSL_FAILURE;
12500
0
    }
12501
12502
0
    if (ssl->options.side == WOLFSSL_CLIENT_END) {
12503
0
        len = ssl->serverFinished_len;
12504
0
        XMEMCPY(buf, ssl->serverFinished, len);
12505
0
    }
12506
0
    else {
12507
0
        len = ssl->clientFinished_len;
12508
0
        XMEMCPY(buf, ssl->clientFinished, len);
12509
0
    }
12510
12511
0
    return len;
12512
0
}
12513
#endif /* WOLFSSL_HAVE_TLS_UNIQUE */
12514
12515
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL) || \
12516
    defined(OPENSSL_ALL)
12517
long wolfSSL_get_verify_result(const WOLFSSL *ssl)
12518
0
{
12519
0
    if (ssl == NULL) {
12520
0
        return WOLFSSL_FAILURE;
12521
0
    }
12522
12523
0
    return (long)ssl->peerVerifyRet;
12524
0
}
12525
#endif
12526
12527
#ifdef OPENSSL_EXTRA
12528
12529
#ifndef NO_WOLFSSL_STUB
12530
/* shows the number of accepts attempted by CTX in it's lifetime */
12531
long wolfSSL_CTX_sess_accept(WOLFSSL_CTX* ctx)
12532
0
{
12533
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_accept");
12534
0
    (void)ctx;
12535
0
    return 0;
12536
0
}
12537
#endif
12538
12539
#ifndef NO_WOLFSSL_STUB
12540
/* shows the number of connects attempted CTX in it's lifetime */
12541
long wolfSSL_CTX_sess_connect(WOLFSSL_CTX* ctx)
12542
0
{
12543
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_connect");
12544
0
    (void)ctx;
12545
0
    return 0;
12546
0
}
12547
#endif
12548
12549
12550
#ifndef NO_WOLFSSL_STUB
12551
/* shows the number of accepts completed by CTX in it's lifetime */
12552
long wolfSSL_CTX_sess_accept_good(WOLFSSL_CTX* ctx)
12553
0
{
12554
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_accept_good");
12555
0
    (void)ctx;
12556
0
    return 0;
12557
0
}
12558
#endif
12559
12560
12561
#ifndef NO_WOLFSSL_STUB
12562
/* shows the number of connects completed by CTX in it's lifetime */
12563
long wolfSSL_CTX_sess_connect_good(WOLFSSL_CTX* ctx)
12564
0
{
12565
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_connect_good");
12566
0
    (void)ctx;
12567
0
    return 0;
12568
0
}
12569
#endif
12570
12571
12572
#ifndef NO_WOLFSSL_STUB
12573
/* shows the number of renegotiation accepts attempted by CTX */
12574
long wolfSSL_CTX_sess_accept_renegotiate(WOLFSSL_CTX* ctx)
12575
0
{
12576
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_accept_renegotiate");
12577
0
    (void)ctx;
12578
0
    return 0;
12579
0
}
12580
#endif
12581
12582
12583
#ifndef NO_WOLFSSL_STUB
12584
/* shows the number of renegotiation accepts attempted by CTX */
12585
long wolfSSL_CTX_sess_connect_renegotiate(WOLFSSL_CTX* ctx)
12586
0
{
12587
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_connect_renegotiate");
12588
0
    (void)ctx;
12589
0
    return 0;
12590
0
}
12591
#endif
12592
12593
12594
#ifndef NO_WOLFSSL_STUB
12595
long wolfSSL_CTX_sess_hits(WOLFSSL_CTX* ctx)
12596
0
{
12597
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_hits");
12598
0
    (void)ctx;
12599
0
    return 0;
12600
0
}
12601
#endif
12602
12603
12604
#ifndef NO_WOLFSSL_STUB
12605
long wolfSSL_CTX_sess_cb_hits(WOLFSSL_CTX* ctx)
12606
0
{
12607
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_cb_hits");
12608
0
    (void)ctx;
12609
0
    return 0;
12610
0
}
12611
#endif
12612
12613
12614
#ifndef NO_WOLFSSL_STUB
12615
long wolfSSL_CTX_sess_cache_full(WOLFSSL_CTX* ctx)
12616
0
{
12617
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_cache_full");
12618
0
    (void)ctx;
12619
0
    return 0;
12620
0
}
12621
#endif
12622
12623
12624
#ifndef NO_WOLFSSL_STUB
12625
long wolfSSL_CTX_sess_misses(WOLFSSL_CTX* ctx)
12626
0
{
12627
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_misses");
12628
0
    (void)ctx;
12629
0
    return 0;
12630
0
}
12631
#endif
12632
12633
12634
#ifndef NO_WOLFSSL_STUB
12635
long wolfSSL_CTX_sess_timeouts(WOLFSSL_CTX* ctx)
12636
0
{
12637
0
    WOLFSSL_STUB("wolfSSL_CTX_sess_timeouts");
12638
0
    (void)ctx;
12639
0
    return 0;
12640
0
}
12641
#endif
12642
12643
int wolfSSL_get_read_ahead(const WOLFSSL* ssl)
12644
0
{
12645
0
    if (ssl == NULL) {
12646
0
        return WOLFSSL_FAILURE;
12647
0
    }
12648
12649
0
    return ssl->readAhead;
12650
0
}
12651
12652
12653
int wolfSSL_set_read_ahead(WOLFSSL* ssl, int v)
12654
0
{
12655
0
    if (ssl == NULL) {
12656
0
        return WOLFSSL_FAILURE;
12657
0
    }
12658
12659
0
    ssl->readAhead = (byte)v;
12660
12661
0
    return WOLFSSL_SUCCESS;
12662
0
}
12663
12664
12665
int wolfSSL_CTX_get_read_ahead(WOLFSSL_CTX* ctx)
12666
0
{
12667
0
    if (ctx == NULL) {
12668
0
        return WOLFSSL_FAILURE;
12669
0
    }
12670
12671
0
    return ctx->readAhead;
12672
0
}
12673
12674
12675
int wolfSSL_CTX_set_read_ahead(WOLFSSL_CTX* ctx, int v)
12676
0
{
12677
0
    if (ctx == NULL) {
12678
0
        return WOLFSSL_FAILURE;
12679
0
    }
12680
12681
0
    ctx->readAhead = (byte)v;
12682
12683
0
    return WOLFSSL_SUCCESS;
12684
0
}
12685
12686
12687
long wolfSSL_CTX_set_tlsext_opaque_prf_input_callback_arg(WOLFSSL_CTX* ctx,
12688
        void* arg)
12689
0
{
12690
0
    if (ctx == NULL) {
12691
0
        return WOLFSSL_FAILURE;
12692
0
    }
12693
12694
0
    ctx->userPRFArg = arg;
12695
0
    return WOLFSSL_SUCCESS;
12696
0
}
12697
12698
#endif /* OPENSSL_EXTRA */
12699
12700
#if defined(OPENSSL_EXTRA) && defined(KEEP_PEER_CERT) && \
12701
    defined(HAVE_EX_DATA) && !defined(NO_FILESYSTEM)
12702
int wolfSSL_cmp_peer_cert_to_file(WOLFSSL* ssl, const char *fname)
12703
0
{
12704
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FATAL_ERROR);
12705
12706
0
    WOLFSSL_ENTER("wolfSSL_cmp_peer_cert_to_file");
12707
0
    if (ssl != NULL && fname != NULL)
12708
0
    {
12709
0
    #ifdef WOLFSSL_SMALL_STACK
12710
0
        byte           staticBuffer[1]; /* force heap usage */
12711
    #else
12712
        byte           staticBuffer[FILE_BUFFER_SIZE];
12713
    #endif
12714
0
        byte*          myBuffer  = staticBuffer;
12715
0
        int            dynamic   = 0;
12716
0
        XFILE          file;
12717
0
        long           sz        = 0;
12718
0
        WOLFSSL_CTX*   ctx       = ssl->ctx;
12719
0
        WOLFSSL_X509*  peer_cert = &ssl->peerCert;
12720
0
        DerBuffer*     fileDer = NULL;
12721
12722
0
        file = XFOPEN(fname, "rb");
12723
0
        if (file == XBADFILE)
12724
0
            return WOLFSSL_BAD_FILE;
12725
12726
0
        if (XFSEEK(file, 0, XSEEK_END) != 0) {
12727
0
            XFCLOSE(file);
12728
0
            return WOLFSSL_BAD_FILE;
12729
0
        }
12730
0
        sz = XFTELL(file);
12731
0
        if (XFSEEK(file, 0, XSEEK_SET) != 0) {
12732
0
            XFCLOSE(file);
12733
0
            return WOLFSSL_BAD_FILE;
12734
0
        }
12735
12736
0
        if (sz > MAX_WOLFSSL_FILE_SIZE || sz < 0) {
12737
0
            WOLFSSL_MSG("cmp_peer_cert_to_file size error");
12738
0
            XFCLOSE(file);
12739
0
            return WOLFSSL_BAD_FILE;
12740
0
        }
12741
12742
0
        if (sz > (long)sizeof(staticBuffer)) {
12743
0
            WOLFSSL_MSG("Getting dynamic buffer");
12744
0
            myBuffer = (byte*)XMALLOC((size_t)sz, ctx->heap, DYNAMIC_TYPE_FILE);
12745
0
            dynamic = 1;
12746
0
        }
12747
12748
0
        if ((myBuffer != NULL) &&
12749
0
            (sz > 0) &&
12750
0
            (XFREAD(myBuffer, 1, (size_t)sz, file) == (size_t)sz) &&
12751
0
            (PemToDer(myBuffer, (long)sz, CERT_TYPE,
12752
0
                      &fileDer, ctx->heap, NULL, NULL) == 0) &&
12753
0
            (fileDer->length != 0) &&
12754
0
            (fileDer->length == peer_cert->derCert->length) &&
12755
0
            (XMEMCMP(peer_cert->derCert->buffer, fileDer->buffer,
12756
0
                                                fileDer->length) == 0))
12757
0
        {
12758
0
            ret = 0;
12759
0
        }
12760
12761
0
        FreeDer(&fileDer);
12762
12763
0
        if (dynamic)
12764
0
            XFREE(myBuffer, ctx->heap, DYNAMIC_TYPE_FILE);
12765
12766
0
        XFCLOSE(file);
12767
0
    }
12768
12769
0
    return ret;
12770
0
}
12771
#endif
12772
12773
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
12774
const WOLFSSL_ObjectInfo wolfssl_object_info[] = {
12775
#ifndef NO_CERTS
12776
    /* oidCertExtType */
12777
    { WC_NID_basic_constraints, BASIC_CA_OID, oidCertExtType,
12778
      "basicConstraints", "X509v3 Basic Constraints"},
12779
    { WC_NID_subject_alt_name, ALT_NAMES_OID, oidCertExtType, "subjectAltName",
12780
      "X509v3 Subject Alternative Name"},
12781
    { WC_NID_crl_distribution_points, CRL_DIST_OID, oidCertExtType,
12782
      "crlDistributionPoints", "X509v3 CRL Distribution Points"},
12783
    { WC_NID_info_access, AUTH_INFO_OID, oidCertExtType, "authorityInfoAccess",
12784
      "Authority Information Access"},
12785
    { WC_NID_authority_key_identifier, AUTH_KEY_OID, oidCertExtType,
12786
      "authorityKeyIdentifier", "X509v3 Authority Key Identifier"},
12787
    { WC_NID_subject_key_identifier, SUBJ_KEY_OID, oidCertExtType,
12788
      "subjectKeyIdentifier", "X509v3 Subject Key Identifier"},
12789
    { WC_NID_key_usage, KEY_USAGE_OID, oidCertExtType, "keyUsage",
12790
      "X509v3 Key Usage"},
12791
    { WC_NID_inhibit_any_policy, INHIBIT_ANY_OID, oidCertExtType,
12792
      "inhibitAnyPolicy", "X509v3 Inhibit Any Policy"},
12793
    { WC_NID_ext_key_usage, EXT_KEY_USAGE_OID, oidCertExtType,
12794
      "extendedKeyUsage", "X509v3 Extended Key Usage"},
12795
    { WC_NID_name_constraints, NAME_CONS_OID, oidCertExtType,
12796
      "nameConstraints", "X509v3 Name Constraints"},
12797
    { WC_NID_certificate_policies, CERT_POLICY_OID, oidCertExtType,
12798
      "certificatePolicies", "X509v3 Certificate Policies"},
12799
12800
    /* oidCertAuthInfoType */
12801
    { WC_NID_ad_OCSP, AIA_OCSP_OID, oidCertAuthInfoType, "OCSP",
12802
      "OCSP"},
12803
    { WC_NID_ad_ca_issuers, AIA_CA_ISSUER_OID, oidCertAuthInfoType,
12804
      "caIssuers", "CA Issuers"},
12805
12806
    /* oidCertPolicyType */
12807
    { WC_NID_any_policy, CP_ANY_OID, oidCertPolicyType, "anyPolicy",
12808
      "X509v3 Any Policy"},
12809
12810
    /* oidCertAltNameType */
12811
    { WC_NID_hw_name_oid, HW_NAME_OID, oidCertAltNameType, "Hardware name",""},
12812
12813
    /* oidCertKeyUseType */
12814
    { WC_NID_anyExtendedKeyUsage, EKU_ANY_OID, oidCertKeyUseType,
12815
      "anyExtendedKeyUsage", "Any Extended Key Usage"},
12816
    { EKU_SERVER_AUTH_OID, EKU_SERVER_AUTH_OID, oidCertKeyUseType,
12817
      "serverAuth", "TLS Web Server Authentication"},
12818
    { EKU_CLIENT_AUTH_OID, EKU_CLIENT_AUTH_OID, oidCertKeyUseType,
12819
      "clientAuth", "TLS Web Client Authentication"},
12820
    { EKU_OCSP_SIGN_OID, EKU_OCSP_SIGN_OID, oidCertKeyUseType,
12821
      "OCSPSigning", "OCSP Signing"},
12822
12823
    /* oidCertNameType */
12824
    { WC_NID_commonName, WC_NAME_COMMON_NAME_OID, oidCertNameType,
12825
      "CN", "commonName"},
12826
#if !defined(WOLFSSL_CERT_REQ)
12827
    { WC_NID_surname, WC_NAME_SURNAME_OID, oidCertNameType, "SN", "surname"},
12828
#endif
12829
    { WC_NID_serialNumber, WC_NAME_SERIAL_NUMBER_OID, oidCertNameType,
12830
      "serialNumber", "serialNumber"},
12831
    { WC_NID_userId, WC_NID_userId, oidCertNameType, "UID", "userid"},
12832
    { WC_NID_countryName, WC_NAME_COUNTRY_NAME_OID, oidCertNameType,
12833
      "C", "countryName"},
12834
    { WC_NID_localityName, WC_NAME_LOCALITY_NAME_OID, oidCertNameType,
12835
      "L", "localityName"},
12836
    { WC_NID_stateOrProvinceName, WC_NAME_STATE_NAME_OID, oidCertNameType,
12837
      "ST", "stateOrProvinceName"},
12838
    { WC_NID_streetAddress, WC_NAME_STREET_ADDRESS_OID, oidCertNameType,
12839
      "street", "streetAddress"},
12840
    { WC_NID_organizationName, WC_NAME_ORGANIZATION_NAME_OID, oidCertNameType,
12841
      "O", "organizationName"},
12842
    { WC_NID_organizationalUnitName, WC_NAME_ORGANIZATION_UNIT_NAME_OID,
12843
      oidCertNameType, "OU", "organizationalUnitName"},
12844
    { WC_NID_title, WC_NAME_TITLE_OID, oidCertNameType, "title", "title"},
12845
    { WC_NID_description, WC_NAME_DESCRIPTION_OID, oidCertNameType,
12846
      "description", "description"},
12847
    { WC_NID_emailAddress, WC_NAME_EMAIL_ADDRESS_OID, oidCertNameType,
12848
      "emailAddress", "emailAddress"},
12849
    { WC_NID_domainComponent, WC_NAME_DOMAIN_COMPONENT_OID, oidCertNameType,
12850
      "DC", "domainComponent"},
12851
    { WC_NID_rfc822Mailbox, WC_NAME_RFC822_MAILBOX_OID, oidCertNameType,
12852
      "rfc822Mailbox", "rfc822Mailbox"},
12853
    { WC_NID_favouriteDrink, WC_NAME_FAVOURITE_DRINK_OID, oidCertNameType,
12854
      "favouriteDrink", "favouriteDrink"},
12855
    { WC_NID_businessCategory, WC_NAME_BUSINESS_CATEGORY_OID, oidCertNameType,
12856
      "businessCategory", "businessCategory"},
12857
    { WC_NID_jurisdictionCountryName, WC_NAME_JURIS_COUNTRY_OID,
12858
      oidCertNameType, "jurisdictionC", "jurisdictionCountryName"},
12859
    { WC_NID_jurisdictionStateOrProvinceName, WC_NAME_JURIS_STATE_PROV_OID,
12860
      oidCertNameType, "jurisdictionST", "jurisdictionStateOrProvinceName"},
12861
    { WC_NID_postalCode, WC_NAME_POSTAL_CODE_OID, oidCertNameType, "postalCode",
12862
      "postalCode"},
12863
    { WC_NID_userId, WC_NAME_USER_ID_OID, oidCertNameType, "UID", "userId"},
12864
    { WC_NID_netscape_cert_type, NETSCAPE_CT_OID, oidCertNameType,
12865
      "nsCertType", "Netscape Cert Type"},
12866
12867
#if defined(WOLFSSL_CERT_REQ) || defined(WOLFSSL_CERT_NAME_ALL)
12868
    { WC_NID_pkcs9_challengePassword, CHALLENGE_PASSWORD_OID,
12869
            oidCsrAttrType, "challengePassword", "challengePassword"},
12870
    { WC_NID_pkcs9_contentType, PKCS9_CONTENT_TYPE_OID,
12871
        oidCsrAttrType, "contentType", "contentType" },
12872
    { WC_NID_pkcs9_unstructuredName, UNSTRUCTURED_NAME_OID,
12873
        oidCsrAttrType, "unstructuredName", "unstructuredName" },
12874
    { WC_NID_name, WC_NAME_NAME_OID, oidCsrAttrType, "name", "name" },
12875
    { WC_NID_surname, SURNAME_OID,
12876
        oidCsrAttrType, "surname", "surname" },
12877
    { WC_NID_givenName, WC_NAME_GIVEN_NAME_OID,
12878
        oidCsrAttrType, "givenName", "givenName" },
12879
    { WC_NID_initials, WC_NAME_INITIALIS_OID,
12880
        oidCsrAttrType, "initials", "initials" },
12881
    { WC_NID_dnQualifier, DNQUALIFIER_OID,
12882
        oidCsrAttrType, "dnQualifer", "dnQualifier" },
12883
#endif
12884
#endif
12885
#ifdef OPENSSL_EXTRA /* OPENSSL_EXTRA_X509_SMALL only needs the above */
12886
        /* oidHashType */
12887
    #ifdef WOLFSSL_MD2
12888
        { WC_NID_md2, MD2h, oidHashType, "MD2", "md2"},
12889
    #endif
12890
    #ifndef NO_MD4
12891
        { WC_NID_md4, MD4h, oidHashType, "MD4", "md4"},
12892
    #endif
12893
    #ifndef NO_MD5
12894
        { WC_NID_md5, MD5h, oidHashType, "MD5", "md5"},
12895
    #endif
12896
    #ifndef NO_SHA
12897
        { WC_NID_sha1, SHAh, oidHashType, "SHA1", "sha1"},
12898
    #endif
12899
    #ifdef WOLFSSL_SHA224
12900
        { WC_NID_sha224, SHA224h, oidHashType, "SHA224", "sha224"},
12901
    #endif
12902
    #ifndef NO_SHA256
12903
        { WC_NID_sha256, SHA256h, oidHashType, "SHA256", "sha256"},
12904
    #endif
12905
    #ifdef WOLFSSL_SHA384
12906
        { WC_NID_sha384, SHA384h, oidHashType, "SHA384", "sha384"},
12907
    #endif
12908
    #ifdef WOLFSSL_SHA512
12909
        { WC_NID_sha512, SHA512h, oidHashType, "SHA512", "sha512"},
12910
    #endif
12911
    #ifdef WOLFSSL_SHA3
12912
        #ifndef WOLFSSL_NOSHA3_224
12913
        { WC_NID_sha3_224, SHA3_224h, oidHashType, "SHA3-224", "sha3-224"},
12914
        #endif
12915
        #ifndef WOLFSSL_NOSHA3_256
12916
        { WC_NID_sha3_256, SHA3_256h, oidHashType, "SHA3-256", "sha3-256"},
12917
        #endif
12918
        #ifndef WOLFSSL_NOSHA3_384
12919
        { WC_NID_sha3_384, SHA3_384h, oidHashType, "SHA3-384", "sha3-384"},
12920
        #endif
12921
        #ifndef WOLFSSL_NOSHA3_512
12922
        { WC_NID_sha3_512, SHA3_512h, oidHashType, "SHA3-512", "sha3-512"},
12923
        #endif
12924
    #endif /* WOLFSSL_SHA3 */
12925
    #ifdef WOLFSSL_SM3
12926
        { WC_NID_sm3, SM3h, oidHashType, "SM3", "sm3"},
12927
    #endif
12928
        /* oidSigType */
12929
    #ifndef NO_DSA
12930
        #ifndef NO_SHA
12931
        { WC_NID_dsaWithSHA1, CTC_SHAwDSA, oidSigType,
12932
          "DSA-SHA1", "dsaWithSHA1"},
12933
        { WC_NID_dsa_with_SHA256, CTC_SHA256wDSA, oidSigType, "dsa_with_SHA256",
12934
          "dsa_with_SHA256"},
12935
        #endif
12936
    #endif /* NO_DSA */
12937
    #ifndef NO_RSA
12938
        #ifdef WOLFSSL_MD2
12939
        { WC_NID_md2WithRSAEncryption, CTC_MD2wRSA, oidSigType, "RSA-MD2",
12940
          "md2WithRSAEncryption"},
12941
        #endif
12942
        #ifndef NO_MD5
12943
        { WC_NID_md5WithRSAEncryption, CTC_MD5wRSA, oidSigType, "RSA-MD5",
12944
          "md5WithRSAEncryption"},
12945
        #endif
12946
        #ifndef NO_SHA
12947
        { WC_NID_sha1WithRSAEncryption, CTC_SHAwRSA, oidSigType, "RSA-SHA1",
12948
          "sha1WithRSAEncryption"},
12949
        #endif
12950
        #ifdef WOLFSSL_SHA224
12951
        { WC_NID_sha224WithRSAEncryption, CTC_SHA224wRSA, oidSigType,
12952
          "RSA-SHA224", "sha224WithRSAEncryption"},
12953
        #endif
12954
        #ifndef NO_SHA256
12955
        { WC_NID_sha256WithRSAEncryption, CTC_SHA256wRSA, oidSigType,
12956
          "RSA-SHA256", "sha256WithRSAEncryption"},
12957
        #endif
12958
        #ifdef WOLFSSL_SHA384
12959
        { WC_NID_sha384WithRSAEncryption, CTC_SHA384wRSA, oidSigType,
12960
          "RSA-SHA384", "sha384WithRSAEncryption"},
12961
        #endif
12962
        #ifdef WOLFSSL_SHA512
12963
        { WC_NID_sha512WithRSAEncryption, CTC_SHA512wRSA, oidSigType,
12964
          "RSA-SHA512", "sha512WithRSAEncryption"},
12965
        #endif
12966
        #ifdef WOLFSSL_SHA3
12967
        #ifndef WOLFSSL_NOSHA3_224
12968
        { WC_NID_RSA_SHA3_224, CTC_SHA3_224wRSA, oidSigType, "RSA-SHA3-224",
12969
          "sha3-224WithRSAEncryption"},
12970
        #endif
12971
        #ifndef WOLFSSL_NOSHA3_256
12972
        { WC_NID_RSA_SHA3_256, CTC_SHA3_256wRSA, oidSigType, "RSA-SHA3-256",
12973
          "sha3-256WithRSAEncryption"},
12974
        #endif
12975
        #ifndef WOLFSSL_NOSHA3_384
12976
        { WC_NID_RSA_SHA3_384, CTC_SHA3_384wRSA, oidSigType, "RSA-SHA3-384",
12977
          "sha3-384WithRSAEncryption"},
12978
        #endif
12979
        #ifndef WOLFSSL_NOSHA3_512
12980
        { WC_NID_RSA_SHA3_512, CTC_SHA3_512wRSA, oidSigType, "RSA-SHA3-512",
12981
          "sha3-512WithRSAEncryption"},
12982
        #endif
12983
        #endif
12984
        #ifdef WC_RSA_PSS
12985
        { WC_NID_rsassaPss, CTC_RSASSAPSS, oidSigType,
12986
          "RSASSA-PSS", "rsassaPss" },
12987
        #endif
12988
    #endif /* NO_RSA */
12989
    #ifdef HAVE_ECC
12990
        #ifndef NO_SHA
12991
        { WC_NID_ecdsa_with_SHA1, CTC_SHAwECDSA, oidSigType, "ecdsa-with-SHA1",
12992
          "shaWithECDSA"},
12993
        #endif
12994
        #ifdef WOLFSSL_SHA224
12995
        { WC_NID_ecdsa_with_SHA224, CTC_SHA224wECDSA, oidSigType,
12996
          "ecdsa-with-SHA224","sha224WithECDSA"},
12997
        #endif
12998
        #ifndef NO_SHA256
12999
        { WC_NID_ecdsa_with_SHA256, CTC_SHA256wECDSA, oidSigType,
13000
          "ecdsa-with-SHA256","sha256WithECDSA"},
13001
        #endif
13002
        #ifdef WOLFSSL_SHA384
13003
        { WC_NID_ecdsa_with_SHA384, CTC_SHA384wECDSA, oidSigType,
13004
          "ecdsa-with-SHA384","sha384WithECDSA"},
13005
        #endif
13006
        #ifdef WOLFSSL_SHA512
13007
        { WC_NID_ecdsa_with_SHA512, CTC_SHA512wECDSA, oidSigType,
13008
          "ecdsa-with-SHA512","sha512WithECDSA"},
13009
        #endif
13010
        #ifdef WOLFSSL_SHA3
13011
        #ifndef WOLFSSL_NOSHA3_224
13012
        { WC_NID_ecdsa_with_SHA3_224, CTC_SHA3_224wECDSA, oidSigType,
13013
          "id-ecdsa-with-SHA3-224", "ecdsa_with_SHA3-224"},
13014
        #endif
13015
        #ifndef WOLFSSL_NOSHA3_256
13016
        { WC_NID_ecdsa_with_SHA3_256, CTC_SHA3_256wECDSA, oidSigType,
13017
          "id-ecdsa-with-SHA3-256", "ecdsa_with_SHA3-256"},
13018
        #endif
13019
        #ifndef WOLFSSL_NOSHA3_384
13020
        { WC_NID_ecdsa_with_SHA3_384, CTC_SHA3_384wECDSA, oidSigType,
13021
          "id-ecdsa-with-SHA3-384", "ecdsa_with_SHA3-384"},
13022
        #endif
13023
        #ifndef WOLFSSL_NOSHA3_512
13024
        { WC_NID_ecdsa_with_SHA3_512, CTC_SHA3_512wECDSA, oidSigType,
13025
          "id-ecdsa-with-SHA3-512", "ecdsa_with_SHA3-512"},
13026
        #endif
13027
        #endif
13028
    #endif /* HAVE_ECC */
13029
13030
        /* oidKeyType */
13031
    #ifndef NO_DSA
13032
        { WC_NID_dsa, DSAk, oidKeyType, "DSA", "dsaEncryption"},
13033
    #endif /* NO_DSA */
13034
    #ifndef NO_RSA
13035
        { WC_NID_rsaEncryption, RSAk, oidKeyType, "rsaEncryption",
13036
          "rsaEncryption"},
13037
    #ifdef WC_RSA_PSS
13038
        { WC_NID_rsassaPss, RSAPSSk, oidKeyType, "RSASSA-PSS", "rsassaPss"},
13039
    #endif
13040
    #endif /* NO_RSA */
13041
    #ifdef HAVE_ECC
13042
        { WC_NID_X9_62_id_ecPublicKey, ECDSAk, oidKeyType, "id-ecPublicKey",
13043
                                                        "id-ecPublicKey"},
13044
    #endif /* HAVE_ECC */
13045
    #ifndef NO_DH
13046
        { WC_NID_dhKeyAgreement, DHk, oidKeyType, "dhKeyAgreement",
13047
          "dhKeyAgreement"},
13048
    #endif
13049
    #ifdef HAVE_ED448
13050
        { WC_NID_ED448, ED448k,  oidKeyType, "ED448", "ED448"},
13051
    #endif
13052
    #ifdef HAVE_ED25519
13053
        { WC_NID_ED25519, ED25519k,  oidKeyType, "ED25519", "ED25519"},
13054
    #endif
13055
    #ifdef HAVE_FALCON
13056
        { CTC_FALCON_LEVEL1, FALCON_LEVEL1k,  oidKeyType, "Falcon Level 1",
13057
                                                          "Falcon Level 1"},
13058
        { CTC_FALCON_LEVEL5, FALCON_LEVEL5k,  oidKeyType, "Falcon Level 5",
13059
                                                          "Falcon Level 5"},
13060
    #endif /* HAVE_FALCON */
13061
    #ifdef HAVE_DILITHIUM
13062
    #ifdef WOLFSSL_DILITHIUM_FIPS204_DRAFT
13063
        { CTC_DILITHIUM_LEVEL2, DILITHIUM_LEVEL2k,  oidKeyType,
13064
          "Dilithium Level 2", "Dilithium Level 2"},
13065
        { CTC_DILITHIUM_LEVEL3, DILITHIUM_LEVEL3k,  oidKeyType,
13066
          "Dilithium Level 3", "Dilithium Level 3"},
13067
        { CTC_DILITHIUM_LEVEL5, DILITHIUM_LEVEL5k,  oidKeyType,
13068
          "Dilithium Level 5", "Dilithium Level 5"},
13069
    #endif /* WOLFSSL_DILITHIUM_FIPS204_DRAFT */
13070
        { CTC_ML_DSA_LEVEL2, ML_DSA_LEVEL2k,  oidKeyType,
13071
          "ML-DSA 44", "ML-DSA 44"},
13072
        { CTC_ML_DSA_LEVEL3, ML_DSA_LEVEL3k,  oidKeyType,
13073
          "ML-DSA 65", "ML-DSA 65"},
13074
        { CTC_ML_DSA_LEVEL5, ML_DSA_LEVEL5k,  oidKeyType,
13075
          "ML-DSA 87", "ML-DSA 87"},
13076
    #endif /* HAVE_DILITHIUM */
13077
13078
        /* oidCurveType */
13079
    #ifdef HAVE_ECC
13080
        { WC_NID_X9_62_prime192v1, ECC_SECP192R1_OID, oidCurveType,
13081
          "prime192v1", "prime192v1"},
13082
        { WC_NID_X9_62_prime192v2, ECC_PRIME192V2_OID, oidCurveType,
13083
          "prime192v2", "prime192v2"},
13084
        { WC_NID_X9_62_prime192v3, ECC_PRIME192V3_OID, oidCurveType,
13085
          "prime192v3", "prime192v3"},
13086
13087
        { WC_NID_X9_62_prime239v1, ECC_PRIME239V1_OID, oidCurveType,
13088
          "prime239v1", "prime239v1"},
13089
        { WC_NID_X9_62_prime239v2, ECC_PRIME239V2_OID, oidCurveType,
13090
          "prime239v2", "prime239v2"},
13091
        { WC_NID_X9_62_prime239v3, ECC_PRIME239V3_OID, oidCurveType,
13092
          "prime239v3", "prime239v3"},
13093
13094
        { WC_NID_X9_62_prime256v1, ECC_SECP256R1_OID, oidCurveType,
13095
          "prime256v1", "prime256v1"},
13096
13097
        { WC_NID_secp112r1, ECC_SECP112R1_OID,  oidCurveType, "secp112r1",
13098
          "secp112r1"},
13099
        { WC_NID_secp112r2, ECC_SECP112R2_OID,  oidCurveType, "secp112r2",
13100
          "secp112r2"},
13101
13102
        { WC_NID_secp128r1, ECC_SECP128R1_OID,  oidCurveType, "secp128r1",
13103
          "secp128r1"},
13104
        { WC_NID_secp128r2, ECC_SECP128R2_OID,  oidCurveType, "secp128r2",
13105
          "secp128r2"},
13106
13107
        { WC_NID_secp160r1, ECC_SECP160R1_OID,  oidCurveType, "secp160r1",
13108
          "secp160r1"},
13109
        { WC_NID_secp160r2, ECC_SECP160R2_OID,  oidCurveType, "secp160r2",
13110
          "secp160r2"},
13111
13112
        { WC_NID_secp224r1, ECC_SECP224R1_OID,  oidCurveType, "secp224r1",
13113
          "secp224r1"},
13114
        { WC_NID_secp384r1, ECC_SECP384R1_OID,  oidCurveType, "secp384r1",
13115
          "secp384r1"},
13116
        { WC_NID_secp521r1, ECC_SECP521R1_OID,  oidCurveType, "secp521r1",
13117
          "secp521r1"},
13118
13119
        { WC_NID_secp160k1, ECC_SECP160K1_OID,  oidCurveType, "secp160k1",
13120
          "secp160k1"},
13121
        { WC_NID_secp192k1, ECC_SECP192K1_OID,  oidCurveType, "secp192k1",
13122
          "secp192k1"},
13123
        { WC_NID_secp224k1, ECC_SECP224K1_OID,  oidCurveType, "secp224k1",
13124
          "secp224k1"},
13125
        { WC_NID_secp256k1, ECC_SECP256K1_OID,  oidCurveType, "secp256k1",
13126
          "secp256k1"},
13127
13128
        { WC_NID_brainpoolP160r1, ECC_BRAINPOOLP160R1_OID,  oidCurveType,
13129
          "brainpoolP160r1", "brainpoolP160r1"},
13130
        { WC_NID_brainpoolP192r1, ECC_BRAINPOOLP192R1_OID,  oidCurveType,
13131
          "brainpoolP192r1", "brainpoolP192r1"},
13132
        { WC_NID_brainpoolP224r1, ECC_BRAINPOOLP224R1_OID,  oidCurveType,
13133
          "brainpoolP224r1", "brainpoolP224r1"},
13134
        { WC_NID_brainpoolP256r1, ECC_BRAINPOOLP256R1_OID,  oidCurveType,
13135
          "brainpoolP256r1", "brainpoolP256r1"},
13136
        { WC_NID_brainpoolP320r1, ECC_BRAINPOOLP320R1_OID,  oidCurveType,
13137
          "brainpoolP320r1", "brainpoolP320r1"},
13138
        { WC_NID_brainpoolP384r1, ECC_BRAINPOOLP384R1_OID,  oidCurveType,
13139
          "brainpoolP384r1", "brainpoolP384r1"},
13140
        { WC_NID_brainpoolP512r1, ECC_BRAINPOOLP512R1_OID,  oidCurveType,
13141
          "brainpoolP512r1", "brainpoolP512r1"},
13142
13143
    #ifdef WOLFSSL_SM2
13144
        { WC_NID_sm2, ECC_SM2P256V1_OID, oidCurveType, "sm2", "sm2"},
13145
    #endif
13146
    #endif /* HAVE_ECC */
13147
13148
        /* oidBlkType */
13149
    #ifdef WOLFSSL_AES_128
13150
        { AES128CBCb, AES128CBCb, oidBlkType, "AES-128-CBC", "aes-128-cbc"},
13151
    #endif
13152
    #ifdef WOLFSSL_AES_192
13153
        { AES192CBCb, AES192CBCb, oidBlkType, "AES-192-CBC", "aes-192-cbc"},
13154
    #endif
13155
    #ifdef WOLFSSL_AES_256
13156
        { AES256CBCb, AES256CBCb, oidBlkType, "AES-256-CBC", "aes-256-cbc"},
13157
    #endif
13158
    #ifndef NO_DES3
13159
        { WC_NID_des, DESb, oidBlkType, "DES-CBC", "des-cbc"},
13160
        { WC_NID_des3, DES3b, oidBlkType, "DES-EDE3-CBC", "des-ede3-cbc"},
13161
    #endif /* !NO_DES3 */
13162
    #if defined(HAVE_CHACHA) && defined(HAVE_POLY1305)
13163
        { WC_NID_chacha20_poly1305, WC_NID_chacha20_poly1305, oidBlkType,
13164
          "ChaCha20-Poly1305", "chacha20-poly1305"},
13165
    #endif
13166
13167
        /* oidOcspType */
13168
    #ifdef HAVE_OCSP
13169
        { WC_NID_id_pkix_OCSP_basic, OCSP_BASIC_OID, oidOcspType,
13170
          "basicOCSPResponse", "Basic OCSP Response"},
13171
        { OCSP_NONCE_OID, OCSP_NONCE_OID, oidOcspType, "Nonce", "OCSP Nonce"},
13172
    #endif /* HAVE_OCSP */
13173
13174
    #ifndef NO_PWDBASED
13175
        /* oidKdfType */
13176
        { PBKDF2_OID, PBKDF2_OID, oidKdfType, "PBKDFv2", "PBKDF2"},
13177
13178
        /* oidPBEType */
13179
        { PBE_SHA1_RC4_128, PBE_SHA1_RC4_128, oidPBEType,
13180
          "PBE-SHA1-RC4-128", "pbeWithSHA1And128BitRC4"},
13181
        { PBE_SHA1_DES, PBE_SHA1_DES, oidPBEType, "PBE-SHA1-DES",
13182
          "pbeWithSHA1AndDES-CBC"},
13183
        { PBE_SHA1_DES3, PBE_SHA1_DES3, oidPBEType, "PBE-SHA1-3DES",
13184
          "pbeWithSHA1And3-KeyTripleDES-CBC"},
13185
    #endif
13186
13187
        /* oidKeyWrapType */
13188
    #ifdef WOLFSSL_AES_128
13189
        { AES128_WRAP, AES128_WRAP, oidKeyWrapType, "AES-128 wrap",
13190
          "aes128-wrap"},
13191
    #endif
13192
    #ifdef WOLFSSL_AES_192
13193
        { AES192_WRAP, AES192_WRAP, oidKeyWrapType, "AES-192 wrap",
13194
          "aes192-wrap"},
13195
    #endif
13196
    #ifdef WOLFSSL_AES_256
13197
        { AES256_WRAP, AES256_WRAP, oidKeyWrapType, "AES-256 wrap",
13198
          "aes256-wrap"},
13199
    #endif
13200
13201
    #ifndef NO_PKCS7
13202
        #ifndef NO_DH
13203
        /* oidCmsKeyAgreeType */
13204
            #ifndef NO_SHA
13205
        { dhSinglePass_stdDH_sha1kdf_scheme, dhSinglePass_stdDH_sha1kdf_scheme,
13206
          oidCmsKeyAgreeType, "dhSinglePass-stdDH-sha1kdf-scheme",
13207
          "dhSinglePass-stdDH-sha1kdf-scheme"},
13208
            #endif
13209
            #ifdef WOLFSSL_SHA224
13210
        { dhSinglePass_stdDH_sha224kdf_scheme,
13211
          dhSinglePass_stdDH_sha224kdf_scheme, oidCmsKeyAgreeType,
13212
          "dhSinglePass-stdDH-sha224kdf-scheme",
13213
          "dhSinglePass-stdDH-sha224kdf-scheme"},
13214
            #endif
13215
            #ifndef NO_SHA256
13216
        { dhSinglePass_stdDH_sha256kdf_scheme,
13217
          dhSinglePass_stdDH_sha256kdf_scheme, oidCmsKeyAgreeType,
13218
          "dhSinglePass-stdDH-sha256kdf-scheme",
13219
          "dhSinglePass-stdDH-sha256kdf-scheme"},
13220
            #endif
13221
            #ifdef WOLFSSL_SHA384
13222
        { dhSinglePass_stdDH_sha384kdf_scheme,
13223
          dhSinglePass_stdDH_sha384kdf_scheme, oidCmsKeyAgreeType,
13224
          "dhSinglePass-stdDH-sha384kdf-scheme",
13225
          "dhSinglePass-stdDH-sha384kdf-scheme"},
13226
            #endif
13227
            #ifdef WOLFSSL_SHA512
13228
        { dhSinglePass_stdDH_sha512kdf_scheme,
13229
          dhSinglePass_stdDH_sha512kdf_scheme, oidCmsKeyAgreeType,
13230
          "dhSinglePass-stdDH-sha512kdf-scheme",
13231
          "dhSinglePass-stdDH-sha512kdf-scheme"},
13232
            #endif
13233
        #endif
13234
    #endif
13235
    #if defined(WOLFSSL_APACHE_HTTPD)
13236
        /* "1.3.6.1.5.5.7.8.7" */
13237
        { WC_NID_id_on_dnsSRV, WOLFSSL_DNS_SRV_SUM, oidCertNameType,
13238
            WOLFSSL_SN_DNS_SRV, WOLFSSL_LN_DNS_SRV },
13239
13240
        /* "1.3.6.1.4.1.311.20.2.3" */
13241
        { WC_NID_ms_upn, WOLFSSL_MS_UPN_SUM, oidCertExtType, WOLFSSL_SN_MS_UPN,
13242
            WOLFSSL_LN_MS_UPN },
13243
13244
        /* "1.3.6.1.5.5.7.1.24" */
13245
        { WC_NID_tlsfeature, WOLFSSL_TLS_FEATURE_SUM, oidTlsExtType,
13246
            WOLFSSL_SN_TLS_FEATURE, WOLFSSL_LN_TLS_FEATURE },
13247
    #endif
13248
#endif /* OPENSSL_EXTRA */
13249
};
13250
13251
#define WOLFSSL_OBJECT_INFO_SZ \
13252
8.63M
                (sizeof(wolfssl_object_info) / sizeof(*wolfssl_object_info))
13253
const size_t wolfssl_object_info_sz = WOLFSSL_OBJECT_INFO_SZ;
13254
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
13255
13256
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
13257
/* Free the dynamically allocated data.
13258
 *
13259
 * p  Pointer to dynamically allocated memory.
13260
 */
13261
void wolfSSL_OPENSSL_free(void* p)
13262
6.81k
{
13263
6.81k
    WOLFSSL_MSG("wolfSSL_OPENSSL_free");
13264
13265
6.81k
    XFREE(p, NULL, DYNAMIC_TYPE_OPENSSL);
13266
6.81k
}
13267
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
13268
13269
#ifdef OPENSSL_EXTRA
13270
13271
void *wolfSSL_OPENSSL_malloc(size_t a)
13272
0
{
13273
0
    return (void *)XMALLOC(a, NULL, DYNAMIC_TYPE_OPENSSL);
13274
0
}
13275
13276
int wolfSSL_OPENSSL_hexchar2int(unsigned char c)
13277
0
{
13278
    /* 'char' is unsigned on some platforms. */
13279
0
    return (int)(signed char)HexCharToByte((char)c);
13280
0
}
13281
13282
unsigned char *wolfSSL_OPENSSL_hexstr2buf(const char *str, long *len)
13283
0
{
13284
0
    unsigned char* targetBuf;
13285
0
    int srcDigitHigh = 0;
13286
0
    int srcDigitLow = 0;
13287
0
    size_t srcLen;
13288
0
    size_t srcIdx = 0;
13289
0
    long targetIdx = 0;
13290
13291
0
    srcLen = XSTRLEN(str);
13292
0
    targetBuf = (unsigned char*)XMALLOC(srcLen / 2, NULL, DYNAMIC_TYPE_OPENSSL);
13293
0
    if (targetBuf == NULL) {
13294
0
        return NULL;
13295
0
    }
13296
13297
0
    while (srcIdx < srcLen) {
13298
0
        if (str[srcIdx] == ':') {
13299
0
            srcIdx++;
13300
0
            continue;
13301
0
        }
13302
13303
0
        srcDigitHigh = wolfSSL_OPENSSL_hexchar2int((unsigned char)str[srcIdx++]);
13304
0
        srcDigitLow = wolfSSL_OPENSSL_hexchar2int((unsigned char)str[srcIdx++]);
13305
0
        if (srcDigitHigh < 0 || srcDigitLow < 0) {
13306
0
            WOLFSSL_MSG("Invalid hex character.");
13307
0
            XFREE(targetBuf, NULL, DYNAMIC_TYPE_OPENSSL);
13308
0
            return NULL;
13309
0
        }
13310
13311
0
        targetBuf[targetIdx++] = (unsigned char)((srcDigitHigh << 4) |
13312
0
                                                  srcDigitLow       );
13313
0
    }
13314
13315
0
    if (len != NULL)
13316
0
        *len = targetIdx;
13317
13318
0
    return targetBuf;
13319
0
}
13320
13321
int wolfSSL_OPENSSL_init_ssl(word64 opts, const WOLFSSL_INIT_SETTINGS *settings)
13322
0
{
13323
0
    (void)opts;
13324
0
    (void)settings;
13325
0
    return wolfSSL_library_init();
13326
0
}
13327
13328
int wolfSSL_OPENSSL_init_crypto(word64 opts,
13329
    const WOLFSSL_INIT_SETTINGS* settings)
13330
0
{
13331
0
    (void)opts;
13332
0
    (void)settings;
13333
0
    return wolfSSL_library_init();
13334
0
}
13335
13336
/* Colon separated list of <public key>+<digest> algorithms.
13337
 * Replaces list in context.
13338
 */
13339
int wolfSSL_CTX_set1_sigalgs_list(WOLFSSL_CTX* ctx, const char* list)
13340
0
{
13341
0
    WOLFSSL_MSG("wolfSSL_CTX_set1_sigalg_list");
13342
13343
0
    if (ctx == NULL || list == NULL) {
13344
0
        WOLFSSL_MSG("Bad function arguments");
13345
0
        return WOLFSSL_FAILURE;
13346
0
    }
13347
13348
0
    if (AllocateCtxSuites(ctx) != 0)
13349
0
        return WOLFSSL_FAILURE;
13350
13351
0
    return SetSuitesHashSigAlgo(ctx->suites, list);
13352
0
}
13353
13354
/* Colon separated list of <public key>+<digest> algorithms.
13355
 * Replaces list in SSL.
13356
 */
13357
int wolfSSL_set1_sigalgs_list(WOLFSSL* ssl, const char* list)
13358
0
{
13359
0
    WOLFSSL_MSG("wolfSSL_set1_sigalg_list");
13360
13361
0
    if (ssl == NULL || list == NULL) {
13362
0
        WOLFSSL_MSG("Bad function arguments");
13363
0
        return WOLFSSL_FAILURE;
13364
0
    }
13365
13366
0
    if (AllocateSuites(ssl) != 0)
13367
0
        return WOLFSSL_FAILURE;
13368
13369
0
    return SetSuitesHashSigAlgo(ssl->suites, list);
13370
0
}
13371
13372
static int HashToNid(byte hashAlgo, int* nid)
13373
0
{
13374
0
    int ret = WOLFSSL_SUCCESS;
13375
13376
    /* Cast for compiler to check everything is implemented */
13377
0
    switch ((enum wc_MACAlgorithm)hashAlgo) {
13378
0
        case no_mac:
13379
0
        case rmd_mac:
13380
0
            *nid = WC_NID_undef;
13381
0
            break;
13382
0
        case md5_mac:
13383
0
            *nid = WC_NID_md5;
13384
0
            break;
13385
0
        case sha_mac:
13386
0
            *nid = WC_NID_sha1;
13387
0
            break;
13388
0
        case sha224_mac:
13389
0
            *nid = WC_NID_sha224;
13390
0
            break;
13391
0
        case sha256_mac:
13392
0
            *nid = WC_NID_sha256;
13393
0
            break;
13394
0
        case sha384_mac:
13395
0
            *nid = WC_NID_sha384;
13396
0
            break;
13397
0
        case sha512_mac:
13398
0
            *nid = WC_NID_sha512;
13399
0
            break;
13400
0
        case blake2b_mac:
13401
0
            *nid = WC_NID_blake2b512;
13402
0
            break;
13403
0
        case sm3_mac:
13404
0
            *nid = WC_NID_sm3;
13405
0
            break;
13406
0
        default:
13407
0
            ret = WOLFSSL_FAILURE;
13408
0
            break;
13409
0
    }
13410
13411
0
    return ret;
13412
0
}
13413
13414
static int SaToNid(byte sa, int* nid)
13415
0
{
13416
0
    int ret = WOLFSSL_SUCCESS;
13417
    /* Cast for compiler to check everything is implemented */
13418
0
    switch ((enum SignatureAlgorithm)sa) {
13419
0
        case anonymous_sa_algo:
13420
0
            *nid = WC_NID_undef;
13421
0
            break;
13422
0
        case rsa_sa_algo:
13423
0
            *nid = WC_NID_rsaEncryption;
13424
0
            break;
13425
0
        case dsa_sa_algo:
13426
0
            *nid = WC_NID_dsa;
13427
0
            break;
13428
0
        case ecc_dsa_sa_algo:
13429
0
        case ecc_brainpool_sa_algo:
13430
0
            *nid = WC_NID_X9_62_id_ecPublicKey;
13431
0
            break;
13432
0
        case rsa_pss_sa_algo:
13433
0
            *nid = WC_NID_rsassaPss;
13434
0
            break;
13435
0
        case ed25519_sa_algo:
13436
0
#ifdef HAVE_ED25519
13437
0
            *nid = WC_NID_ED25519;
13438
#else
13439
            ret = WOLFSSL_FAILURE;
13440
#endif
13441
0
            break;
13442
0
        case rsa_pss_pss_algo:
13443
0
            *nid = WC_NID_rsassaPss;
13444
0
            break;
13445
0
        case ed448_sa_algo:
13446
0
#ifdef HAVE_ED448
13447
0
            *nid = WC_NID_ED448;
13448
#else
13449
            ret = WOLFSSL_FAILURE;
13450
#endif
13451
0
            break;
13452
0
        case falcon_level1_sa_algo:
13453
0
            *nid = CTC_FALCON_LEVEL1;
13454
0
            break;
13455
0
        case falcon_level5_sa_algo:
13456
0
            *nid = CTC_FALCON_LEVEL5;
13457
0
            break;
13458
0
        case dilithium_level2_sa_algo:
13459
0
            *nid = CTC_ML_DSA_LEVEL2;
13460
0
            break;
13461
0
        case dilithium_level3_sa_algo:
13462
0
            *nid = CTC_ML_DSA_LEVEL3;
13463
0
            break;
13464
0
        case dilithium_level5_sa_algo:
13465
0
            *nid = CTC_ML_DSA_LEVEL5;
13466
0
            break;
13467
0
        case sm2_sa_algo:
13468
0
            *nid = WC_NID_sm2;
13469
0
            break;
13470
0
        case invalid_sa_algo:
13471
0
        case any_sa_algo:
13472
0
        default:
13473
0
            ret = WOLFSSL_FAILURE;
13474
0
            break;
13475
0
    }
13476
0
    return ret;
13477
0
}
13478
13479
/* This API returns the hash selected. */
13480
int wolfSSL_get_signature_nid(WOLFSSL *ssl, int* nid)
13481
0
{
13482
0
    WOLFSSL_MSG("wolfSSL_get_signature_nid");
13483
13484
0
    if (ssl == NULL || nid == NULL) {
13485
0
        WOLFSSL_MSG("Bad function arguments");
13486
0
        return WOLFSSL_FAILURE;
13487
0
    }
13488
13489
0
    return HashToNid(ssl->options.hashAlgo, nid);
13490
0
}
13491
13492
/* This API returns the signature selected. */
13493
int wolfSSL_get_signature_type_nid(const WOLFSSL* ssl, int* nid)
13494
0
{
13495
0
    WOLFSSL_MSG("wolfSSL_get_signature_type_nid");
13496
13497
0
    if (ssl == NULL || nid == NULL) {
13498
0
        WOLFSSL_MSG("Bad function arguments");
13499
0
        return WOLFSSL_FAILURE;
13500
0
    }
13501
13502
0
    return SaToNid(ssl->options.sigAlgo, nid);
13503
0
}
13504
13505
int wolfSSL_get_peer_signature_nid(WOLFSSL* ssl, int* nid)
13506
0
{
13507
0
    WOLFSSL_MSG("wolfSSL_get_peer_signature_nid");
13508
13509
0
    if (ssl == NULL || nid == NULL) {
13510
0
        WOLFSSL_MSG("Bad function arguments");
13511
0
        return WOLFSSL_FAILURE;
13512
0
    }
13513
13514
0
    return HashToNid(ssl->options.peerHashAlgo, nid);
13515
0
}
13516
13517
int wolfSSL_get_peer_signature_type_nid(const WOLFSSL* ssl, int* nid)
13518
0
{
13519
0
    WOLFSSL_MSG("wolfSSL_get_peer_signature_type_nid");
13520
13521
0
    if (ssl == NULL || nid == NULL) {
13522
0
        WOLFSSL_MSG("Bad function arguments");
13523
0
        return WOLFSSL_FAILURE;
13524
0
    }
13525
13526
0
    return SaToNid(ssl->options.peerSigAlgo, nid);
13527
0
}
13528
13529
#ifdef HAVE_ECC
13530
13531
#if defined(WOLFSSL_TLS13) && defined(HAVE_SUPPORTED_CURVES)
13532
int wolfSSL_CTX_set1_groups_list(WOLFSSL_CTX *ctx, const char *list)
13533
0
{
13534
0
    if (!ctx || !list) {
13535
0
        return WOLFSSL_FAILURE;
13536
0
    }
13537
13538
0
    return set_curves_list(NULL, ctx, list, 0);
13539
0
}
13540
13541
int wolfSSL_set1_groups_list(WOLFSSL *ssl, const char *list)
13542
0
{
13543
0
    if (!ssl || !list) {
13544
0
        return WOLFSSL_FAILURE;
13545
0
    }
13546
13547
0
    return set_curves_list(ssl, NULL, list, 0);
13548
0
}
13549
#endif /* WOLFSSL_TLS13 */
13550
13551
#endif /* HAVE_ECC */
13552
13553
#endif /* OPENSSL_EXTRA */
13554
13555
#ifdef WOLFSSL_ALT_CERT_CHAINS
13556
int wolfSSL_is_peer_alt_cert_chain(const WOLFSSL* ssl)
13557
{
13558
    int isUsing = 0;
13559
    if (ssl)
13560
        isUsing = ssl->options.usingAltCertChain;
13561
    return isUsing;
13562
}
13563
#endif /* WOLFSSL_ALT_CERT_CHAINS */
13564
13565
13566
#ifdef SESSION_CERTS
13567
13568
#ifdef WOLFSSL_ALT_CERT_CHAINS
13569
/* Get peer's alternate certificate chain */
13570
WOLFSSL_X509_CHAIN* wolfSSL_get_peer_alt_chain(WOLFSSL* ssl)
13571
{
13572
    WOLFSSL_ENTER("wolfSSL_get_peer_alt_chain");
13573
    if (ssl)
13574
        return &ssl->session->altChain;
13575
13576
    return 0;
13577
}
13578
#endif /* WOLFSSL_ALT_CERT_CHAINS */
13579
13580
13581
/* Get peer's certificate chain */
13582
WOLFSSL_X509_CHAIN* wolfSSL_get_peer_chain(WOLFSSL* ssl)
13583
{
13584
    WOLFSSL_ENTER("wolfSSL_get_peer_chain");
13585
    if (ssl)
13586
        return &ssl->session->chain;
13587
13588
    return 0;
13589
}
13590
13591
13592
/* Get peer's certificate chain total count */
13593
int wolfSSL_get_chain_count(WOLFSSL_X509_CHAIN* chain)
13594
{
13595
    WOLFSSL_ENTER("wolfSSL_get_chain_count");
13596
    if (chain)
13597
        return chain->count;
13598
13599
    return 0;
13600
}
13601
13602
13603
/* Get peer's ASN.1 DER certificate at index (idx) length in bytes */
13604
int wolfSSL_get_chain_length(WOLFSSL_X509_CHAIN* chain, int idx)
13605
{
13606
    WOLFSSL_ENTER("wolfSSL_get_chain_length");
13607
    if (chain)
13608
        return chain->certs[idx].length;
13609
13610
    return 0;
13611
}
13612
13613
13614
/* Get peer's ASN.1 DER certificate at index (idx) */
13615
byte* wolfSSL_get_chain_cert(WOLFSSL_X509_CHAIN* chain, int idx)
13616
{
13617
    WOLFSSL_ENTER("wolfSSL_get_chain_cert");
13618
    if (chain)
13619
        return chain->certs[idx].buffer;
13620
13621
    return 0;
13622
}
13623
13624
13625
/* Get peer's wolfSSL X509 certificate at index (idx) */
13626
WOLFSSL_X509* wolfSSL_get_chain_X509(WOLFSSL_X509_CHAIN* chain, int idx)
13627
{
13628
    int          ret = 0;
13629
    WOLFSSL_X509* x509 = NULL;
13630
    WC_DECLARE_VAR(cert, DecodedCert, 1, 0);
13631
13632
    WOLFSSL_ENTER("wolfSSL_get_chain_X509");
13633
    if (chain != NULL && idx < MAX_CHAIN_DEPTH) {
13634
    #ifdef WOLFSSL_SMALL_STACK
13635
        cert = (DecodedCert*)XMALLOC(sizeof(DecodedCert), NULL,
13636
                                                       DYNAMIC_TYPE_DCERT);
13637
        if (cert != NULL)
13638
    #endif
13639
        {
13640
            InitDecodedCert(cert, chain->certs[idx].buffer,
13641
                                  (word32)chain->certs[idx].length, NULL);
13642
13643
            if ((ret = ParseCertRelative(cert, CERT_TYPE, 0, NULL, NULL)) != 0) {
13644
                WOLFSSL_MSG("Failed to parse cert");
13645
            }
13646
            else {
13647
                x509 = (WOLFSSL_X509*)XMALLOC(sizeof(WOLFSSL_X509), NULL,
13648
                                                             DYNAMIC_TYPE_X509);
13649
                if (x509 == NULL) {
13650
                    WOLFSSL_MSG("Failed alloc X509");
13651
                }
13652
                else {
13653
                    InitX509(x509, 1, NULL);
13654
13655
                    if ((ret = CopyDecodedToX509(x509, cert)) != 0) {
13656
                        WOLFSSL_MSG("Failed to copy decoded");
13657
                        wolfSSL_X509_free(x509);
13658
                        x509 = NULL;
13659
                    }
13660
                }
13661
            }
13662
13663
            FreeDecodedCert(cert);
13664
            WC_FREE_VAR_EX(cert, NULL, DYNAMIC_TYPE_DCERT);
13665
        }
13666
    }
13667
    (void)ret;
13668
13669
    return x509;
13670
}
13671
13672
13673
/* Get peer's PEM certificate at index (idx), output to buffer if inLen big
13674
   enough else return error (-1). If buffer is NULL only calculate
13675
   outLen. Output length is in *outLen WOLFSSL_SUCCESS on ok */
13676
int  wolfSSL_get_chain_cert_pem(WOLFSSL_X509_CHAIN* chain, int idx,
13677
                               unsigned char* buf, int inLen, int* outLen)
13678
{
13679
#if defined(WOLFSSL_PEM_TO_DER) || defined(WOLFSSL_DER_TO_PEM)
13680
    const char* header = NULL;
13681
    const char* footer = NULL;
13682
    int headerLen;
13683
    int footerLen;
13684
    int i;
13685
    int err;
13686
    word32 szNeeded = 0;
13687
13688
    WOLFSSL_ENTER("wolfSSL_get_chain_cert_pem");
13689
    if (!chain || !outLen || idx < 0 || idx >= wolfSSL_get_chain_count(chain))
13690
        return BAD_FUNC_ARG;
13691
13692
    err = wc_PemGetHeaderFooter(CERT_TYPE, &header, &footer);
13693
    if (err != 0)
13694
        return err;
13695
13696
    headerLen = (int)XSTRLEN(header);
13697
    footerLen = (int)XSTRLEN(footer);
13698
13699
    /* Null output buffer return size needed in outLen */
13700
    if(!buf) {
13701
        if(Base64_Encode(chain->certs[idx].buffer,
13702
                    (word32)chain->certs[idx].length,
13703
                    NULL, &szNeeded) != WC_NO_ERR_TRACE(LENGTH_ONLY_E))
13704
            return WOLFSSL_FAILURE;
13705
        *outLen = (int)szNeeded + headerLen + footerLen;
13706
        return WC_NO_ERR_TRACE(LENGTH_ONLY_E);
13707
    }
13708
13709
    /* don't even try if inLen too short */
13710
    if (inLen < headerLen + footerLen + chain->certs[idx].length)
13711
        return BAD_FUNC_ARG;
13712
13713
    /* header */
13714
    if (XMEMCPY(buf, header, (size_t)headerLen) == NULL)
13715
        return WOLFSSL_FATAL_ERROR;
13716
13717
    i = headerLen;
13718
13719
    /* body */
13720
    *outLen = inLen;  /* input to Base64_Encode */
13721
    if ( (err = Base64_Encode(chain->certs[idx].buffer,
13722
                       (word32)chain->certs[idx].length, buf + i,
13723
                       (word32*)outLen)) < 0)
13724
        return err;
13725
    i += *outLen;
13726
13727
    /* footer */
13728
    if ( (i + footerLen) > inLen)
13729
        return BAD_FUNC_ARG;
13730
    if (XMEMCPY(buf + i, footer, (size_t)footerLen) == NULL)
13731
        return WOLFSSL_FATAL_ERROR;
13732
    *outLen += headerLen + footerLen;
13733
13734
    return WOLFSSL_SUCCESS;
13735
#else
13736
    (void)chain;
13737
    (void)idx;
13738
    (void)buf;
13739
    (void)inLen;
13740
    (void)outLen;
13741
    return WOLFSSL_FAILURE;
13742
#endif /* WOLFSSL_PEM_TO_DER || WOLFSSL_DER_TO_PEM */
13743
}
13744
13745
#endif /* SESSION_CERTS */
13746
13747
#ifdef HAVE_FUZZER
13748
void wolfSSL_SetFuzzerCb(WOLFSSL* ssl, CallbackFuzzer cbf, void* fCtx)
13749
{
13750
    if (ssl) {
13751
        ssl->fuzzerCb  = cbf;
13752
        ssl->fuzzerCtx = fCtx;
13753
    }
13754
}
13755
#endif
13756
13757
#ifndef NO_CERTS
13758
#ifdef  HAVE_PK_CALLBACKS
13759
13760
/* callback for premaster secret generation */
13761
void  wolfSSL_CTX_SetGenPreMasterCb(WOLFSSL_CTX* ctx, CallbackGenPreMaster cb)
13762
{
13763
    if (ctx)
13764
        ctx->GenPreMasterCb = cb;
13765
}
13766
/* Set premaster secret generation callback context */
13767
void  wolfSSL_SetGenPreMasterCtx(WOLFSSL* ssl, void *ctx)
13768
{
13769
    if (ssl)
13770
        ssl->GenPreMasterCtx = ctx;
13771
}
13772
/* Get premaster secret generation callback context */
13773
void* wolfSSL_GetGenPreMasterCtx(WOLFSSL* ssl)
13774
{
13775
    if (ssl)
13776
        return ssl->GenPreMasterCtx;
13777
13778
    return NULL;
13779
}
13780
13781
/* callback for master secret generation */
13782
void  wolfSSL_CTX_SetGenMasterSecretCb(WOLFSSL_CTX* ctx,
13783
    CallbackGenMasterSecret cb)
13784
{
13785
    if (ctx)
13786
        ctx->GenMasterCb = cb;
13787
}
13788
/* Set master secret generation callback context */
13789
void  wolfSSL_SetGenMasterSecretCtx(WOLFSSL* ssl, void *ctx)
13790
{
13791
    if (ssl)
13792
        ssl->GenMasterCtx = ctx;
13793
}
13794
/* Get master secret generation callback context */
13795
void* wolfSSL_GetGenMasterSecretCtx(WOLFSSL* ssl)
13796
{
13797
    if (ssl)
13798
        return ssl->GenMasterCtx;
13799
13800
    return NULL;
13801
}
13802
13803
/* callback for extended master secret generation */
13804
void  wolfSSL_CTX_SetGenExtMasterSecretCb(WOLFSSL_CTX* ctx,
13805
    CallbackGenExtMasterSecret cb)
13806
{
13807
    if (ctx)
13808
        ctx->GenExtMasterCb = cb;
13809
}
13810
/* Set extended master secret generation callback context */
13811
void  wolfSSL_SetGenExtMasterSecretCtx(WOLFSSL* ssl, void *ctx)
13812
{
13813
    if (ssl)
13814
        ssl->GenExtMasterCtx = ctx;
13815
}
13816
/* Get extended master secret generation callback context */
13817
void* wolfSSL_GetGenExtMasterSecretCtx(WOLFSSL* ssl)
13818
{
13819
    if (ssl)
13820
        return ssl->GenExtMasterCtx;
13821
13822
    return NULL;
13823
}
13824
13825
13826
/* callback for session key generation */
13827
void  wolfSSL_CTX_SetGenSessionKeyCb(WOLFSSL_CTX* ctx, CallbackGenSessionKey cb)
13828
{
13829
    if (ctx)
13830
        ctx->GenSessionKeyCb = cb;
13831
}
13832
/* Set session key generation callback context */
13833
void  wolfSSL_SetGenSessionKeyCtx(WOLFSSL* ssl, void *ctx)
13834
{
13835
    if (ssl)
13836
        ssl->GenSessionKeyCtx = ctx;
13837
}
13838
/* Get session key generation callback context */
13839
void* wolfSSL_GetGenSessionKeyCtx(WOLFSSL* ssl)
13840
{
13841
    if (ssl)
13842
        return ssl->GenSessionKeyCtx;
13843
13844
    return NULL;
13845
}
13846
13847
/* callback for setting encryption keys */
13848
void  wolfSSL_CTX_SetEncryptKeysCb(WOLFSSL_CTX* ctx, CallbackEncryptKeys cb)
13849
{
13850
    if (ctx)
13851
        ctx->EncryptKeysCb = cb;
13852
}
13853
/* Set encryption keys callback context */
13854
void  wolfSSL_SetEncryptKeysCtx(WOLFSSL* ssl, void *ctx)
13855
{
13856
    if (ssl)
13857
        ssl->EncryptKeysCtx = ctx;
13858
}
13859
/* Get encryption keys callback context */
13860
void* wolfSSL_GetEncryptKeysCtx(WOLFSSL* ssl)
13861
{
13862
    if (ssl)
13863
        return ssl->EncryptKeysCtx;
13864
13865
    return NULL;
13866
}
13867
13868
/* callback for Tls finished */
13869
/* the callback can be used to build TLS Finished message if enabled */
13870
void  wolfSSL_CTX_SetTlsFinishedCb(WOLFSSL_CTX* ctx, CallbackTlsFinished cb)
13871
{
13872
    if (ctx)
13873
        ctx->TlsFinishedCb = cb;
13874
}
13875
/* Set Tls finished callback context */
13876
void  wolfSSL_SetTlsFinishedCtx(WOLFSSL* ssl, void *ctx)
13877
{
13878
    if (ssl)
13879
        ssl->TlsFinishedCtx = ctx;
13880
}
13881
/* Get Tls finished callback context */
13882
void* wolfSSL_GetTlsFinishedCtx(WOLFSSL* ssl)
13883
{
13884
    if (ssl)
13885
        return ssl->TlsFinishedCtx;
13886
13887
    return NULL;
13888
}
13889
#if !defined(WOLFSSL_NO_TLS12) && !defined(WOLFSSL_AEAD_ONLY)
13890
/* callback for verify data */
13891
void  wolfSSL_CTX_SetVerifyMacCb(WOLFSSL_CTX* ctx, CallbackVerifyMac cb)
13892
{
13893
    if (ctx)
13894
        ctx->VerifyMacCb = cb;
13895
}
13896
13897
/* Set set keys callback context */
13898
void  wolfSSL_SetVerifyMacCtx(WOLFSSL* ssl, void *ctx)
13899
{
13900
    if (ssl)
13901
        ssl->VerifyMacCtx = ctx;
13902
}
13903
/* Get set  keys callback context */
13904
void* wolfSSL_GetVerifyMacCtx(WOLFSSL* ssl)
13905
{
13906
    if (ssl)
13907
        return ssl->VerifyMacCtx;
13908
13909
    return NULL;
13910
}
13911
#endif /* !WOLFSSL_NO_TLS12 && !WOLFSSL_AEAD_ONLY */
13912
13913
void wolfSSL_CTX_SetHKDFExpandLabelCb(WOLFSSL_CTX* ctx,
13914
                                      CallbackHKDFExpandLabel cb)
13915
{
13916
    if (ctx)
13917
        ctx->HKDFExpandLabelCb = cb;
13918
}
13919
#ifdef WOLFSSL_PUBLIC_ASN
13920
void wolfSSL_CTX_SetProcessPeerCertCb(WOLFSSL_CTX* ctx,
13921
                                        CallbackProcessPeerCert cb)
13922
{
13923
    if (ctx)
13924
        ctx->ProcessPeerCertCb = cb;
13925
}
13926
#endif /* WOLFSSL_PUBLIC_ASN */
13927
void wolfSSL_CTX_SetProcessServerSigKexCb(WOLFSSL_CTX* ctx,
13928
                                       CallbackProcessServerSigKex cb)
13929
{
13930
    if (ctx)
13931
        ctx->ProcessServerSigKexCb = cb;
13932
}
13933
void wolfSSL_CTX_SetPerformTlsRecordProcessingCb(WOLFSSL_CTX* ctx,
13934
                                          CallbackPerformTlsRecordProcessing cb)
13935
{
13936
    if (ctx)
13937
        ctx->PerformTlsRecordProcessingCb = cb;
13938
}
13939
#endif /* HAVE_PK_CALLBACKS */
13940
#endif /* NO_CERTS */
13941
13942
#if defined(HAVE_PK_CALLBACKS) && defined(HAVE_HKDF)
13943
13944
void wolfSSL_CTX_SetHKDFExtractCb(WOLFSSL_CTX* ctx, CallbackHKDFExtract cb)
13945
{
13946
    if (ctx)
13947
        ctx->HkdfExtractCb = cb;
13948
}
13949
13950
void wolfSSL_SetHKDFExtractCtx(WOLFSSL* ssl, void *ctx)
13951
{
13952
    if (ssl)
13953
        ssl->HkdfExtractCtx = ctx;
13954
}
13955
13956
void* wolfSSL_GetHKDFExtractCtx(WOLFSSL* ssl)
13957
{
13958
    if (ssl)
13959
        return ssl->HkdfExtractCtx;
13960
13961
    return NULL;
13962
}
13963
#endif /* HAVE_PK_CALLBACKS && HAVE_HKDF */
13964
13965
#ifdef WOLFSSL_HAVE_WOLFSCEP
13966
    /* Used by autoconf to see if wolfSCEP is available */
13967
    void wolfSSL_wolfSCEP(void) {}
13968
#endif
13969
13970
13971
#ifdef WOLFSSL_HAVE_CERT_SERVICE
13972
    /* Used by autoconf to see if cert service is available */
13973
    void wolfSSL_cert_service(void) {}
13974
#endif
13975
13976
#if (defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)) && \
13977
    !defined(WOLFCRYPT_ONLY)
13978
13979
    /* NID variables are dependent on compatibility header files currently
13980
     *
13981
     * returns a pointer to a new WOLFSSL_ASN1_OBJECT struct on success and NULL
13982
     *         on fail
13983
     */
13984
13985
    WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_nid2obj(int id)
13986
4.38k
    {
13987
4.38k
        return wolfSSL_OBJ_nid2obj_ex(id, NULL);
13988
4.38k
    }
13989
13990
13991
    WOLFSSL_LOCAL WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_nid2obj_ex(int id,
13992
                                                WOLFSSL_ASN1_OBJECT* arg_obj)
13993
291k
    {
13994
291k
        word32 oidSz = 0;
13995
291k
        int nid = 0;
13996
291k
        const byte* oid;
13997
291k
        word32 type = 0;
13998
291k
        WOLFSSL_ASN1_OBJECT* obj = arg_obj;
13999
291k
        byte objBuf[MAX_OID_SZ + MAX_LENGTH_SZ + 1]; /* +1 for object tag */
14000
291k
        word32 objSz = 0;
14001
291k
        const char* sName = NULL;
14002
291k
        int i;
14003
14004
#ifdef WOLFSSL_DEBUG_OPENSSL
14005
        WOLFSSL_ENTER("wolfSSL_OBJ_nid2obj");
14006
#endif
14007
14008
8.33M
        for (i = 0; i < (int)WOLFSSL_OBJECT_INFO_SZ; i++) {
14009
8.33M
            if (wolfssl_object_info[i].nid == id) {
14010
291k
                nid = id;
14011
291k
                id = wolfssl_object_info[i].id;
14012
291k
                sName = wolfssl_object_info[i].sName;
14013
291k
                type = wolfssl_object_info[i].type;
14014
291k
                break;
14015
291k
            }
14016
8.33M
        }
14017
291k
        if (i == (int)WOLFSSL_OBJECT_INFO_SZ) {
14018
325
            WOLFSSL_MSG("NID not in table");
14019
        #ifdef WOLFSSL_QT
14020
            sName = NULL;
14021
            type = (word32)id;
14022
        #else
14023
325
            return NULL;
14024
325
        #endif
14025
325
        }
14026
14027
291k
    #ifdef HAVE_ECC
14028
291k
         if (type == 0 && wc_ecc_get_oid((word32)id, &oid, &oidSz) > 0) {
14029
0
             type = oidCurveType;
14030
0
         }
14031
291k
    #endif /* HAVE_ECC */
14032
14033
291k
        if (sName != NULL) {
14034
291k
            if (XSTRLEN(sName) > WOLFSSL_MAX_SNAME - 1) {
14035
0
                WOLFSSL_MSG("Attempted short name is too large");
14036
0
                return NULL;
14037
0
            }
14038
291k
        }
14039
14040
291k
        oid = OidFromId((word32)id, type, &oidSz);
14041
14042
        /* set object ID to buffer */
14043
291k
        if (obj == NULL){
14044
78.9k
            obj = wolfSSL_ASN1_OBJECT_new();
14045
78.9k
            if (obj == NULL) {
14046
0
                WOLFSSL_MSG("Issue creating WOLFSSL_ASN1_OBJECT struct");
14047
0
                return NULL;
14048
0
            }
14049
78.9k
        }
14050
291k
        obj->nid     = nid;
14051
291k
        obj->type    = id;
14052
291k
        obj->grp     = (int)type;
14053
14054
291k
        obj->sName[0] = '\0';
14055
291k
        if (sName != NULL) {
14056
291k
            XMEMCPY(obj->sName, (char*)sName, XSTRLEN((char*)sName));
14057
291k
        }
14058
14059
291k
        objBuf[0] = ASN_OBJECT_ID; objSz++;
14060
291k
        objSz += SetLength(oidSz, objBuf + 1);
14061
291k
        if (oidSz) {
14062
4.06k
            XMEMCPY(objBuf + objSz, oid, oidSz);
14063
4.06k
            objSz     += oidSz;
14064
4.06k
        }
14065
14066
291k
        if (obj->objSz == 0 || objSz != obj->objSz) {
14067
78.9k
            obj->objSz = objSz;
14068
78.9k
            if(((obj->dynamic & WOLFSSL_ASN1_DYNAMIC_DATA) != 0) ||
14069
78.9k
                                                           (obj->obj == NULL)) {
14070
78.9k
                if (obj->obj != NULL)
14071
0
                    XFREE((byte*)obj->obj, NULL, DYNAMIC_TYPE_ASN1);
14072
78.9k
                obj->obj = (byte*)XMALLOC(obj->objSz, NULL, DYNAMIC_TYPE_ASN1);
14073
78.9k
                if (obj->obj == NULL) {
14074
0
                    wolfSSL_ASN1_OBJECT_free(obj);
14075
0
                    return NULL;
14076
0
                }
14077
78.9k
                obj->dynamic |= WOLFSSL_ASN1_DYNAMIC_DATA;
14078
78.9k
            }
14079
0
            else {
14080
0
                obj->dynamic &= (unsigned char)~WOLFSSL_ASN1_DYNAMIC_DATA;
14081
0
            }
14082
78.9k
        }
14083
291k
        XMEMCPY((byte*)obj->obj, objBuf, obj->objSz);
14084
14085
291k
        (void)type;
14086
14087
291k
        return obj;
14088
291k
    }
14089
14090
    static const char* oid_translate_num_to_str(const char* oid)
14091
0
    {
14092
0
        const struct oid_dict {
14093
0
            const char* num;
14094
0
            const char* desc;
14095
0
        } oid_dict[] = {
14096
0
            { "2.5.29.37.0",       "Any Extended Key Usage" },
14097
0
            { "1.3.6.1.5.5.7.3.1", "TLS Web Server Authentication" },
14098
0
            { "1.3.6.1.5.5.7.3.2", "TLS Web Client Authentication" },
14099
0
            { "1.3.6.1.5.5.7.3.3", "Code Signing" },
14100
0
            { "1.3.6.1.5.5.7.3.4", "E-mail Protection" },
14101
0
            { "1.3.6.1.5.5.7.3.8", "Time Stamping" },
14102
0
            { "1.3.6.1.5.5.7.3.9", "OCSP Signing" },
14103
0
            { NULL, NULL }
14104
0
        };
14105
0
        const struct oid_dict* idx;
14106
14107
0
        for (idx = oid_dict; idx->num != NULL; idx++) {
14108
0
            if (!XSTRCMP(oid, idx->num)) {
14109
0
                return idx->desc;
14110
0
            }
14111
0
        }
14112
0
        return NULL;
14113
0
    }
14114
14115
    static int wolfssl_obj2txt_numeric(char *buf, int bufLen,
14116
                                       const WOLFSSL_ASN1_OBJECT *a)
14117
0
    {
14118
0
        int bufSz;
14119
0
        int    length;
14120
0
        word32 idx = 0;
14121
0
        byte   tag;
14122
14123
0
        if (GetASNTag(a->obj, &idx, &tag, a->objSz) != 0) {
14124
0
            return WOLFSSL_FAILURE;
14125
0
        }
14126
14127
0
        if (tag != ASN_OBJECT_ID) {
14128
0
            WOLFSSL_MSG("Bad ASN1 Object");
14129
0
            return WOLFSSL_FAILURE;
14130
0
        }
14131
14132
0
        if (GetLength((const byte*)a->obj, &idx, &length,
14133
0
                       a->objSz) < 0 || length < 0) {
14134
0
            return ASN_PARSE_E;
14135
0
        }
14136
14137
0
        if (bufLen < MAX_OID_STRING_SZ) {
14138
0
            bufSz = bufLen - 1;
14139
0
        }
14140
0
        else {
14141
0
            bufSz = MAX_OID_STRING_SZ;
14142
0
        }
14143
14144
0
        if ((bufSz = DecodePolicyOID(buf, (word32)bufSz, a->obj + idx,
14145
0
                    (word32)length)) <= 0) {
14146
0
            WOLFSSL_MSG("Error decoding OID");
14147
0
            return WOLFSSL_FAILURE;
14148
0
        }
14149
14150
0
        buf[bufSz] = '\0';
14151
14152
0
        return bufSz;
14153
0
    }
14154
14155
    /* If no_name is one then use numerical form, otherwise short name.
14156
     *
14157
     * Returns the buffer size on success, WOLFSSL_FAILURE on error
14158
     */
14159
    int wolfSSL_OBJ_obj2txt(char *buf, int bufLen, const WOLFSSL_ASN1_OBJECT *a,
14160
                            int no_name)
14161
0
    {
14162
0
        int bufSz;
14163
0
        const char* desc;
14164
0
        const char* name;
14165
14166
0
        WOLFSSL_ENTER("wolfSSL_OBJ_obj2txt");
14167
14168
0
        if (buf == NULL || bufLen <= 1 || a == NULL) {
14169
0
            WOLFSSL_MSG("Bad input argument");
14170
0
            return WOLFSSL_FAILURE;
14171
0
        }
14172
14173
0
        if (no_name == 1) {
14174
0
            return wolfssl_obj2txt_numeric(buf, bufLen, a);
14175
0
        }
14176
14177
        /* return long name unless using x509small, then return short name */
14178
#if defined(OPENSSL_EXTRA_X509_SMALL) && !defined(OPENSSL_EXTRA)
14179
        name = a->sName;
14180
#else
14181
0
        name = wolfSSL_OBJ_nid2ln(wolfSSL_OBJ_obj2nid(a));
14182
0
#endif
14183
14184
0
        if (name == NULL) {
14185
0
            WOLFSSL_MSG("Name not found");
14186
0
            bufSz = 0;
14187
0
        }
14188
0
        else if (XSTRLEN(name) + 1 < (word32)bufLen - 1) {
14189
0
            bufSz = (int)XSTRLEN(name);
14190
0
        }
14191
0
        else {
14192
0
            bufSz = bufLen - 1;
14193
0
        }
14194
0
        if (bufSz) {
14195
0
            XMEMCPY(buf, name, (size_t)bufSz);
14196
0
        }
14197
0
        else if (a->type == WOLFSSL_GEN_DNS || a->type == WOLFSSL_GEN_EMAIL ||
14198
0
                 a->type == WOLFSSL_GEN_URI) {
14199
0
            bufSz = (int)XSTRLEN((const char*)a->obj);
14200
0
            XMEMCPY(buf, a->obj, min((word32)bufSz, (word32)bufLen));
14201
0
        }
14202
0
        else if ((bufSz = wolfssl_obj2txt_numeric(buf, bufLen, a)) > 0) {
14203
0
            if ((desc = oid_translate_num_to_str(buf))) {
14204
0
                bufSz = (int)XSTRLEN(desc);
14205
0
                bufSz = (int)min((word32)bufSz,(word32) bufLen - 1);
14206
0
                XMEMCPY(buf, desc, (size_t)bufSz);
14207
0
            }
14208
0
        }
14209
0
        else {
14210
0
            bufSz = 0;
14211
0
        }
14212
14213
0
        buf[bufSz] = '\0';
14214
14215
0
        return bufSz;
14216
0
    }
14217
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
14218
14219
#if defined(OPENSSL_EXTRA) || defined(HAVE_LIGHTY) || \
14220
    defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) || \
14221
    defined(WOLFSSL_NGINX) || defined(HAVE_POCO_LIB) || \
14222
    defined(WOLFSSL_HAPROXY) || defined(WOLFSSL_WPAS_SMALL)
14223
    /* Returns the long name that corresponds with an ASN1_OBJECT nid value.
14224
     *  n : NID value of ASN1_OBJECT to search */
14225
    const char* wolfSSL_OBJ_nid2ln(int n)
14226
199
    {
14227
199
        const WOLFSSL_ObjectInfo *obj_info = wolfssl_object_info;
14228
199
        size_t i;
14229
199
        WOLFSSL_ENTER("wolfSSL_OBJ_nid2ln");
14230
9.99k
        for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++, obj_info++) {
14231
9.99k
            if (obj_info->nid == n) {
14232
199
                return obj_info->lName;
14233
199
            }
14234
9.99k
        }
14235
0
        WOLFSSL_MSG("NID not found in table");
14236
0
        return NULL;
14237
199
    }
14238
#endif /* OPENSSL_EXTRA, HAVE_LIGHTY, WOLFSSL_MYSQL_COMPATIBLE, HAVE_STUNNEL,
14239
          WOLFSSL_NGINX, HAVE_POCO_LIB, WOLFSSL_HAPROXY, WOLFSSL_WPAS_SMALL */
14240
14241
#if defined(OPENSSL_EXTRA) || defined(HAVE_LIGHTY) || \
14242
    defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) || \
14243
    defined(WOLFSSL_NGINX) || defined(HAVE_POCO_LIB) || \
14244
    defined(WOLFSSL_HAPROXY)
14245
    /* Return the corresponding short name for the nid <n>.
14246
     * or NULL if short name can't be found.
14247
     */
14248
0
    const char * wolfSSL_OBJ_nid2sn(int n) {
14249
0
        const WOLFSSL_ObjectInfo *obj_info = wolfssl_object_info;
14250
0
        size_t i;
14251
0
        WOLFSSL_ENTER("wolfSSL_OBJ_nid2sn");
14252
14253
0
        if (n == WC_NID_md5) {
14254
            /* WC_NID_surname == WC_NID_md5 and WC_NID_surname comes before WC_NID_md5 in
14255
             * wolfssl_object_info. As a result, the loop below will incorrectly
14256
             * return "SN" instead of "MD5." WC_NID_surname isn't the true OpenSSL
14257
             * NID, but other functions rely on this table and modifying it to
14258
             * conform with OpenSSL's NIDs isn't trivial. */
14259
0
             return "MD5";
14260
0
        }
14261
0
        for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++, obj_info++) {
14262
0
            if (obj_info->nid == n) {
14263
0
                return obj_info->sName;
14264
0
            }
14265
0
        }
14266
0
        WOLFSSL_MSG_EX("SN not found (nid:%d)",n);
14267
0
        return NULL;
14268
0
    }
14269
14270
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
14271
0
    int wolfSSL_OBJ_sn2nid(const char *sn) {
14272
0
        WOLFSSL_ENTER("wolfSSL_OBJ_sn2nid");
14273
0
        if (sn == NULL)
14274
0
            return WC_NID_undef;
14275
0
        return wc_OBJ_sn2nid(sn);
14276
0
    }
14277
#endif
14278
14279
    size_t wolfSSL_OBJ_length(const WOLFSSL_ASN1_OBJECT* o)
14280
0
    {
14281
0
        size_t ret = 0;
14282
0
        int err = 0;
14283
0
        word32 idx = 0;
14284
0
        int len = 0;
14285
14286
0
        WOLFSSL_ENTER("wolfSSL_OBJ_length");
14287
14288
0
        if (o == NULL || o->obj == NULL) {
14289
0
            WOLFSSL_MSG("Bad argument.");
14290
0
            err = 1;
14291
0
        }
14292
14293
0
        if (err == 0 && GetASNObjectId(o->obj, &idx, &len, o->objSz)) {
14294
0
            WOLFSSL_MSG("Error parsing ASN.1 header.");
14295
0
            err = 1;
14296
0
        }
14297
0
        if (err == 0) {
14298
0
            ret = (size_t)len;
14299
0
        }
14300
14301
0
        WOLFSSL_LEAVE("wolfSSL_OBJ_length", (int)ret);
14302
14303
0
        return ret;
14304
0
    }
14305
14306
    const unsigned char* wolfSSL_OBJ_get0_data(const WOLFSSL_ASN1_OBJECT* o)
14307
0
    {
14308
0
        const unsigned char* ret = NULL;
14309
0
        int err = 0;
14310
0
        word32 idx = 0;
14311
0
        int len = 0;
14312
14313
0
        WOLFSSL_ENTER("wolfSSL_OBJ_get0_data");
14314
14315
0
        if (o == NULL || o->obj == NULL) {
14316
0
            WOLFSSL_MSG("Bad argument.");
14317
0
            err = 1;
14318
0
        }
14319
14320
0
        if (err == 0 && GetASNObjectId(o->obj, &idx, &len, o->objSz)) {
14321
0
            WOLFSSL_MSG("Error parsing ASN.1 header.");
14322
0
            err = 1;
14323
0
        }
14324
0
        if (err == 0) {
14325
0
            ret = o->obj + idx;
14326
0
        }
14327
14328
0
        return ret;
14329
0
    }
14330
14331
14332
    /* Gets the NID value that corresponds with the ASN1 object.
14333
     *
14334
     * o ASN1 object to get NID of
14335
     *
14336
     * Return NID on success and a negative value on failure
14337
     */
14338
    int wolfSSL_OBJ_obj2nid(const WOLFSSL_ASN1_OBJECT *o)
14339
0
    {
14340
0
        word32 oid = 0;
14341
0
        word32 idx = 0;
14342
0
        int ret;
14343
14344
#ifdef WOLFSSL_DEBUG_OPENSSL
14345
        WOLFSSL_ENTER("wolfSSL_OBJ_obj2nid");
14346
#endif
14347
14348
0
        if (o == NULL) {
14349
0
            return WOLFSSL_FATAL_ERROR;
14350
0
        }
14351
14352
        #ifdef WOLFSSL_QT
14353
        if (o->grp == oidCertExtType) {
14354
            /* If nid is an unknown extension, return WC_NID_undef */
14355
            if (wolfSSL_OBJ_nid2sn(o->nid) == NULL)
14356
                return WC_NID_undef;
14357
        }
14358
        #endif
14359
14360
0
        if (o->nid > 0)
14361
0
            return o->nid;
14362
0
        if ((ret = GetObjectId(o->obj, &idx, &oid,
14363
0
                                    (word32)o->grp, o->objSz)) < 0) {
14364
0
            if (ret == WC_NO_ERR_TRACE(ASN_OBJECT_ID_E)) {
14365
                /* Put ASN object tag in front and try again */
14366
0
                int len = SetObjectId((int)o->objSz, NULL) + (int)o->objSz;
14367
0
                byte* buf = (byte*)XMALLOC((size_t)len, NULL,
14368
0
                                            DYNAMIC_TYPE_TMP_BUFFER);
14369
0
                if (!buf) {
14370
0
                    WOLFSSL_MSG("malloc error");
14371
0
                    return WOLFSSL_FATAL_ERROR;
14372
0
                }
14373
0
                idx = (word32)SetObjectId((int)o->objSz, buf);
14374
0
                XMEMCPY(buf + idx, o->obj, o->objSz);
14375
0
                idx = 0;
14376
0
                ret = GetObjectId(buf, &idx, &oid, (word32)o->grp, (word32)len);
14377
0
                XFREE(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
14378
0
                if (ret < 0) {
14379
0
                    WOLFSSL_MSG("Issue getting OID of object");
14380
0
                    return WOLFSSL_FATAL_ERROR;
14381
0
                }
14382
0
            }
14383
0
            else {
14384
0
                WOLFSSL_MSG("Issue getting OID of object");
14385
0
                return WOLFSSL_FATAL_ERROR;
14386
0
            }
14387
0
        }
14388
14389
0
        return oid2nid(oid, o->grp);
14390
0
    }
14391
14392
    /* Return the corresponding NID for the long name <ln>
14393
     * or WC_NID_undef if NID can't be found.
14394
     */
14395
    int wolfSSL_OBJ_ln2nid(const char *ln)
14396
0
    {
14397
0
        const WOLFSSL_ObjectInfo *obj_info = wolfssl_object_info;
14398
0
        size_t lnlen;
14399
0
        WOLFSSL_ENTER("wolfSSL_OBJ_ln2nid");
14400
0
        if (ln && (lnlen = XSTRLEN(ln)) > 0) {
14401
            /* Accept input like "/commonName=" */
14402
0
            if (ln[0] == '/') {
14403
0
                ln++;
14404
0
                lnlen--;
14405
0
            }
14406
0
            if (lnlen) {
14407
0
                size_t i;
14408
14409
0
                if (ln[lnlen-1] == '=') {
14410
0
                    lnlen--;
14411
0
                }
14412
0
                for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++, obj_info++) {
14413
0
                    if (lnlen == XSTRLEN(obj_info->lName) &&
14414
0
                            XSTRNCMP(ln, obj_info->lName, lnlen) == 0) {
14415
0
                        return obj_info->nid;
14416
0
                    }
14417
0
                }
14418
0
            }
14419
0
        }
14420
0
        return WC_NID_undef;
14421
0
    }
14422
14423
    /* compares two objects, return 0 if equal */
14424
    int wolfSSL_OBJ_cmp(const WOLFSSL_ASN1_OBJECT* a,
14425
                        const WOLFSSL_ASN1_OBJECT* b)
14426
0
    {
14427
0
        WOLFSSL_ENTER("wolfSSL_OBJ_cmp");
14428
14429
0
        if (a && b && a->obj && b->obj) {
14430
0
            if (a->objSz == b->objSz) {
14431
0
                return XMEMCMP(a->obj, b->obj, a->objSz);
14432
0
            }
14433
0
            else if (a->type == EXT_KEY_USAGE_OID ||
14434
0
                     b->type == EXT_KEY_USAGE_OID) {
14435
                /* Special case for EXT_KEY_USAGE_OID so that
14436
                 * cmp will be treated as a substring search */
14437
                /* Used in libest to check for id-kp-cmcRA in
14438
                 * EXT_KEY_USAGE extension */
14439
0
                unsigned int idx;
14440
0
                const byte* s; /* shorter */
14441
0
                unsigned int sLen;
14442
0
                const byte* l; /* longer */
14443
0
                unsigned int lLen;
14444
0
                if (a->objSz > b->objSz) {
14445
0
                    s = b->obj; sLen = b->objSz;
14446
0
                    l = a->obj; lLen = a->objSz;
14447
0
                }
14448
0
                else {
14449
0
                    s = a->obj; sLen = a->objSz;
14450
0
                    l = b->obj; lLen = b->objSz;
14451
0
                }
14452
0
                for (idx = 0; idx <= lLen - sLen; idx++) {
14453
0
                    if (XMEMCMP(l + idx, s, sLen) == 0) {
14454
                        /* Found substring */
14455
0
                        return 0;
14456
0
                    }
14457
0
                }
14458
0
            }
14459
0
        }
14460
14461
0
        return WOLFSSL_FATAL_ERROR;
14462
0
    }
14463
#endif /* OPENSSL_EXTRA, HAVE_LIGHTY, WOLFSSL_MYSQL_COMPATIBLE, HAVE_STUNNEL,
14464
          WOLFSSL_NGINX, HAVE_POCO_LIB, WOLFSSL_HAPROXY */
14465
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL) || \
14466
    defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) || \
14467
    defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) || \
14468
    defined(HAVE_POCO_LIB) || defined(WOLFSSL_HAPROXY)
14469
    /* Gets the NID value that is related to the OID string passed in. Example
14470
     * string would be "2.5.29.14" for subject key ID.
14471
     *
14472
     * returns NID value on success and WC_NID_undef on error
14473
     */
14474
    int wolfSSL_OBJ_txt2nid(const char* s)
14475
0
    {
14476
0
        unsigned int i;
14477
0
    #ifdef WOLFSSL_CERT_EXT
14478
0
        int ret;
14479
0
        unsigned int sum = 0;
14480
0
        unsigned int outSz = MAX_OID_SZ;
14481
0
        unsigned char out[MAX_OID_SZ];
14482
14483
0
        XMEMSET(out, 0, sizeof(out));
14484
0
    #endif
14485
14486
0
        WOLFSSL_ENTER("wolfSSL_OBJ_txt2nid");
14487
14488
0
        if (s == NULL) {
14489
0
            return WC_NID_undef;
14490
0
        }
14491
14492
0
    #ifdef WOLFSSL_CERT_EXT
14493
0
        ret = EncodePolicyOID(out, &outSz, s, NULL);
14494
0
        if (ret == 0) {
14495
            /* sum OID */
14496
0
            sum = wc_oid_sum(out, outSz);
14497
0
        }
14498
0
    #endif /* WOLFSSL_CERT_EXT */
14499
14500
        /* get the group that the OID's sum is in
14501
         * @TODO possible conflict with multiples */
14502
0
        for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++) {
14503
0
            int len;
14504
0
        #ifdef WOLFSSL_CERT_EXT
14505
0
            if (ret == 0) {
14506
0
                if (wolfssl_object_info[i].id == (int)sum) {
14507
0
                    return wolfssl_object_info[i].nid;
14508
0
                }
14509
0
            }
14510
0
        #endif
14511
14512
            /* try as a short name */
14513
0
            len = (int)XSTRLEN(s);
14514
0
            if ((int)XSTRLEN(wolfssl_object_info[i].sName) == len &&
14515
0
                XSTRNCMP(wolfssl_object_info[i].sName, s, (word32)len) == 0) {
14516
0
                return wolfssl_object_info[i].nid;
14517
0
            }
14518
14519
            /* try as a long name */
14520
0
            if ((int)XSTRLEN(wolfssl_object_info[i].lName) == len &&
14521
0
                XSTRNCMP(wolfssl_object_info[i].lName, s, (word32)len) == 0) {
14522
0
                return wolfssl_object_info[i].nid;
14523
0
            }
14524
0
        }
14525
14526
0
        return WC_NID_undef;
14527
0
    }
14528
#endif
14529
#if defined(OPENSSL_EXTRA) || defined(HAVE_LIGHTY) || \
14530
    defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) || \
14531
    defined(WOLFSSL_NGINX) || defined(HAVE_POCO_LIB) || \
14532
    defined(WOLFSSL_HAPROXY)
14533
14534
    /* Creates new ASN1_OBJECT from short name, long name, or text
14535
     * representation of oid. If no_name is 0, then short name, long name, and
14536
     * numerical value of oid are interpreted. If no_name is 1, then only the
14537
     * numerical value of the oid is interpreted.
14538
     *
14539
     * Returns pointer to ASN1_OBJECT on success, or NULL on error.
14540
     */
14541
#if defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_CERT_GEN)
14542
    WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_txt2obj(const char* s, int no_name)
14543
    {
14544
        int i, ret;
14545
        int nid = WC_NID_undef;
14546
        unsigned int outSz = MAX_OID_SZ;
14547
        unsigned char out[MAX_OID_SZ];
14548
        WOLFSSL_ASN1_OBJECT* obj;
14549
14550
        WOLFSSL_ENTER("wolfSSL_OBJ_txt2obj");
14551
14552
        if (s == NULL)
14553
            return NULL;
14554
14555
        /* If s is numerical value, try to sum oid */
14556
        ret = EncodePolicyOID(out, &outSz, s, NULL);
14557
        if (ret == 0 && outSz > 0) {
14558
            /* If numerical encode succeeded then just
14559
             * create object from that because sums are
14560
             * not unique and can cause confusion. */
14561
            obj = wolfSSL_ASN1_OBJECT_new();
14562
            if (obj == NULL) {
14563
                WOLFSSL_MSG("Issue creating WOLFSSL_ASN1_OBJECT struct");
14564
                return NULL;
14565
            }
14566
            obj->dynamic |= WOLFSSL_ASN1_DYNAMIC;
14567
            obj->obj = (byte*)XMALLOC(1 + MAX_LENGTH_SZ + outSz, NULL,
14568
                    DYNAMIC_TYPE_ASN1);
14569
            if (obj->obj == NULL) {
14570
                wolfSSL_ASN1_OBJECT_free(obj);
14571
                return NULL;
14572
            }
14573
            obj->dynamic |= WOLFSSL_ASN1_DYNAMIC_DATA;
14574
            i = SetObjectId((int)outSz, (byte*)obj->obj);
14575
            XMEMCPY((byte*)obj->obj + i, out, outSz);
14576
            obj->objSz = (word32)i + outSz;
14577
            return obj;
14578
        }
14579
14580
        /* TODO: update short names in wolfssl_object_info and check OID sums
14581
           are correct */
14582
        for (i = 0; i < (int)WOLFSSL_OBJECT_INFO_SZ; i++) {
14583
            /* Short name, long name, and numerical value are interpreted */
14584
            if (no_name == 0 &&
14585
                ((XSTRCMP(s, wolfssl_object_info[i].sName) == 0) ||
14586
                 (XSTRCMP(s, wolfssl_object_info[i].lName) == 0)))
14587
            {
14588
                    nid = wolfssl_object_info[i].nid;
14589
            }
14590
        }
14591
14592
        if (nid != WC_NID_undef)
14593
            return wolfSSL_OBJ_nid2obj(nid);
14594
14595
        return NULL;
14596
    }
14597
#endif
14598
14599
    /* compatibility function. Its intended use is to remove OID's from an
14600
     * internal table that have been added with OBJ_create. wolfSSL manages its
14601
     * own internal OID values and does not currently support OBJ_create. */
14602
    void wolfSSL_OBJ_cleanup(void)
14603
0
    {
14604
0
        WOLFSSL_ENTER("wolfSSL_OBJ_cleanup");
14605
0
    }
14606
14607
    #ifndef NO_WOLFSSL_STUB
14608
    int wolfSSL_OBJ_create(const char *oid, const char *sn, const char *ln)
14609
0
    {
14610
0
        (void)oid;
14611
0
        (void)sn;
14612
0
        (void)ln;
14613
0
        WOLFSSL_STUB("wolfSSL_OBJ_create");
14614
0
        return WOLFSSL_FAILURE;
14615
0
    }
14616
    #endif
14617
14618
    void wolfSSL_set_verify_depth(WOLFSSL *ssl, int depth)
14619
0
    {
14620
0
    #if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
14621
0
        WOLFSSL_ENTER("wolfSSL_set_verify_depth");
14622
0
        ssl->options.verifyDepth = (byte)depth;
14623
0
    #endif
14624
0
    }
14625
14626
#endif /* OPENSSL_ALL || HAVE_LIGHTY || WOLFSSL_MYSQL_COMPATIBLE ||
14627
    HAVE_STUNNEL || WOLFSSL_NGINX || HAVE_POCO_LIB || WOLFSSL_HAPROXY */
14628
14629
#ifdef OPENSSL_EXTRA
14630
14631
/* wolfSSL uses negative values for error states. This function returns an
14632
 * unsigned type so the value returned is the absolute value of the error.
14633
 */
14634
unsigned long wolfSSL_ERR_peek_last_error_line(const char **file, int *line)
14635
0
{
14636
0
    WOLFSSL_ENTER("wolfSSL_ERR_peek_last_error");
14637
14638
0
    (void)line;
14639
0
    (void)file;
14640
0
#ifdef WOLFSSL_HAVE_ERROR_QUEUE
14641
0
    {
14642
0
        int ret;
14643
14644
0
        if ((ret = wc_PeekErrorNode(-1, file, NULL, line)) < 0) {
14645
0
            WOLFSSL_MSG("Issue peeking at error node in queue");
14646
0
            return 0;
14647
0
        }
14648
0
    #if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) \
14649
0
        || defined(WOLFSSL_HAPROXY)
14650
0
        if (ret == -WC_NO_ERR_TRACE(ASN_NO_PEM_HEADER))
14651
0
            return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE;
14652
0
    #endif
14653
    #if defined(OPENSSL_ALL) && defined(WOLFSSL_PYTHON)
14654
        if (ret == ASN1_R_HEADER_TOO_LONG) {
14655
            return (ERR_LIB_ASN1 << 24) | ASN1_R_HEADER_TOO_LONG;
14656
        }
14657
    #endif
14658
0
        return (unsigned long)ret;
14659
0
    }
14660
#else
14661
    return (unsigned long)(0 - NOT_COMPILED_IN);
14662
#endif
14663
0
}
14664
14665
#endif /* OPENSSL_EXTRA */
14666
14667
#ifdef HAVE_EX_DATA_CRYPTO
14668
CRYPTO_EX_cb_ctx* crypto_ex_cb_ctx_session = NULL;
14669
14670
static int crypto_ex_cb_new(CRYPTO_EX_cb_ctx** dst, long ctx_l, void* ctx_ptr,
14671
        WOLFSSL_CRYPTO_EX_new* new_func, WOLFSSL_CRYPTO_EX_dup* dup_func,
14672
        WOLFSSL_CRYPTO_EX_free* free_func)
14673
0
{
14674
0
    CRYPTO_EX_cb_ctx* new_ctx = (CRYPTO_EX_cb_ctx*)XMALLOC(
14675
0
            sizeof(CRYPTO_EX_cb_ctx), NULL, DYNAMIC_TYPE_OPENSSL);
14676
0
    if (new_ctx == NULL)
14677
0
        return WOLFSSL_FATAL_ERROR;
14678
0
    new_ctx->ctx_l = ctx_l;
14679
0
    new_ctx->ctx_ptr = ctx_ptr;
14680
0
    new_ctx->new_func = new_func;
14681
0
    new_ctx->free_func = free_func;
14682
0
    new_ctx->dup_func = dup_func;
14683
0
    new_ctx->next = NULL;
14684
    /* Push to end of list */
14685
0
    while (*dst != NULL)
14686
0
        dst = &(*dst)->next;
14687
0
    *dst = new_ctx;
14688
0
    return 0;
14689
0
}
14690
14691
void crypto_ex_cb_free(CRYPTO_EX_cb_ctx* cb_ctx)
14692
16
{
14693
16
    while (cb_ctx != NULL) {
14694
0
        CRYPTO_EX_cb_ctx* next = cb_ctx->next;
14695
0
        XFREE(cb_ctx, NULL, DYNAMIC_TYPE_OPENSSL);
14696
0
        cb_ctx = next;
14697
0
    }
14698
16
}
14699
14700
void crypto_ex_cb_setup_new_data(void *new_obj, CRYPTO_EX_cb_ctx* cb_ctx,
14701
        WOLFSSL_CRYPTO_EX_DATA* ex_data)
14702
0
{
14703
0
    int idx = 0;
14704
0
    for (; cb_ctx != NULL; idx++, cb_ctx = cb_ctx->next) {
14705
0
        if (cb_ctx->new_func != NULL)
14706
0
            cb_ctx->new_func(new_obj, NULL, ex_data, idx, cb_ctx->ctx_l,
14707
0
                    cb_ctx->ctx_ptr);
14708
0
    }
14709
0
}
14710
14711
int crypto_ex_cb_dup_data(const WOLFSSL_CRYPTO_EX_DATA *in,
14712
        WOLFSSL_CRYPTO_EX_DATA *out, CRYPTO_EX_cb_ctx* cb_ctx)
14713
0
{
14714
0
    int idx = 0;
14715
0
    for (; cb_ctx != NULL; idx++, cb_ctx = cb_ctx->next) {
14716
0
        if (cb_ctx->dup_func != NULL) {
14717
0
            void* ptr = wolfSSL_CRYPTO_get_ex_data(in, idx);
14718
0
            if (!cb_ctx->dup_func(out, in,
14719
0
                    &ptr, idx,
14720
0
                    cb_ctx->ctx_l, cb_ctx->ctx_ptr)) {
14721
0
                return WOLFSSL_FAILURE;
14722
0
            }
14723
0
            wolfSSL_CRYPTO_set_ex_data(out, idx, ptr);
14724
0
        }
14725
0
    }
14726
0
    return WOLFSSL_SUCCESS;
14727
0
}
14728
14729
void crypto_ex_cb_free_data(void *obj, CRYPTO_EX_cb_ctx* cb_ctx,
14730
        WOLFSSL_CRYPTO_EX_DATA* ex_data)
14731
76.1k
{
14732
76.1k
    int idx = 0;
14733
76.1k
    for (; cb_ctx != NULL; idx++, cb_ctx = cb_ctx->next) {
14734
0
        if (cb_ctx->free_func != NULL)
14735
0
            cb_ctx->free_func(obj, NULL, ex_data, idx, cb_ctx->ctx_l,
14736
0
                    cb_ctx->ctx_ptr);
14737
0
    }
14738
76.1k
}
14739
14740
/**
14741
 * get_ex_new_index is a helper function for the following
14742
 * xx_get_ex_new_index functions:
14743
 *  - wolfSSL_CRYPTO_get_ex_new_index
14744
 *  - wolfSSL_CTX_get_ex_new_index
14745
 *  - wolfSSL_get_ex_new_index
14746
 * Issues a unique index number for the specified class-index.
14747
 * Returns an index number greater or equal to zero on success,
14748
 * -1 on failure.
14749
 */
14750
int wolfssl_get_ex_new_index(int class_index, long ctx_l, void* ctx_ptr,
14751
        WOLFSSL_CRYPTO_EX_new* new_func, WOLFSSL_CRYPTO_EX_dup* dup_func,
14752
        WOLFSSL_CRYPTO_EX_free* free_func)
14753
0
{
14754
    /* index counter for each class index*/
14755
0
    static int ctx_idx = 0;
14756
0
    static int ssl_idx = 0;
14757
0
    static int ssl_session_idx = 0;
14758
0
    static int x509_idx = 0;
14759
14760
0
    int idx = -1;
14761
14762
0
    switch(class_index) {
14763
0
        case WOLF_CRYPTO_EX_INDEX_SSL:
14764
0
            WOLFSSL_CRYPTO_EX_DATA_IGNORE_PARAMS(ctx_l, ctx_ptr, new_func,
14765
0
                    dup_func, free_func);
14766
0
            idx = ssl_idx++;
14767
0
            break;
14768
0
        case WOLF_CRYPTO_EX_INDEX_SSL_CTX:
14769
0
            WOLFSSL_CRYPTO_EX_DATA_IGNORE_PARAMS(ctx_l, ctx_ptr, new_func,
14770
0
                    dup_func, free_func);
14771
0
            idx = ctx_idx++;
14772
0
            break;
14773
0
        case WOLF_CRYPTO_EX_INDEX_X509:
14774
0
            WOLFSSL_CRYPTO_EX_DATA_IGNORE_PARAMS(ctx_l, ctx_ptr, new_func,
14775
0
                    dup_func, free_func);
14776
0
            idx = x509_idx++;
14777
0
            break;
14778
0
        case WOLF_CRYPTO_EX_INDEX_SSL_SESSION:
14779
0
            if (crypto_ex_cb_new(&crypto_ex_cb_ctx_session, ctx_l, ctx_ptr,
14780
0
                    new_func, dup_func, free_func) != 0)
14781
0
                return WOLFSSL_FATAL_ERROR;
14782
0
            idx = ssl_session_idx++;
14783
0
            break;
14784
14785
        /* following class indexes are not supoprted */
14786
0
        case WOLF_CRYPTO_EX_INDEX_X509_STORE:
14787
0
        case WOLF_CRYPTO_EX_INDEX_X509_STORE_CTX:
14788
0
        case WOLF_CRYPTO_EX_INDEX_DH:
14789
0
        case WOLF_CRYPTO_EX_INDEX_DSA:
14790
0
        case WOLF_CRYPTO_EX_INDEX_EC_KEY:
14791
0
        case WOLF_CRYPTO_EX_INDEX_RSA:
14792
0
        case WOLF_CRYPTO_EX_INDEX_ENGINE:
14793
0
        case WOLF_CRYPTO_EX_INDEX_UI:
14794
0
        case WOLF_CRYPTO_EX_INDEX_BIO:
14795
0
        case WOLF_CRYPTO_EX_INDEX_APP:
14796
0
        case WOLF_CRYPTO_EX_INDEX_UI_METHOD:
14797
0
        case WOLF_CRYPTO_EX_INDEX_DRBG:
14798
0
        default:
14799
0
            break;
14800
0
    }
14801
0
    if (idx >= MAX_EX_DATA)
14802
0
        return WOLFSSL_FATAL_ERROR;
14803
0
    return idx;
14804
0
}
14805
#endif /* HAVE_EX_DATA_CRYPTO */
14806
14807
#ifdef HAVE_EX_DATA_CRYPTO
14808
int wolfSSL_CTX_get_ex_new_index(long idx, void* arg,
14809
                                 WOLFSSL_CRYPTO_EX_new* new_func,
14810
                                 WOLFSSL_CRYPTO_EX_dup* dup_func,
14811
                                 WOLFSSL_CRYPTO_EX_free* free_func)
14812
0
{
14813
14814
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_ex_new_index");
14815
14816
0
    return wolfssl_get_ex_new_index(WOLF_CRYPTO_EX_INDEX_SSL_CTX, idx, arg,
14817
0
                                    new_func, dup_func, free_func);
14818
0
}
14819
14820
/* Return the index that can be used for the WOLFSSL structure to store
14821
 * application data.
14822
 *
14823
 */
14824
int wolfSSL_get_ex_new_index(long argValue, void* arg,
14825
        WOLFSSL_CRYPTO_EX_new* cb1, WOLFSSL_CRYPTO_EX_dup* cb2,
14826
        WOLFSSL_CRYPTO_EX_free* cb3)
14827
0
{
14828
0
    WOLFSSL_ENTER("wolfSSL_get_ex_new_index");
14829
14830
0
    return wolfssl_get_ex_new_index(WOLF_CRYPTO_EX_INDEX_SSL, argValue, arg,
14831
0
            cb1, cb2, cb3);
14832
0
}
14833
#endif /* HAVE_EX_DATA_CRYPTO */
14834
14835
#ifdef OPENSSL_EXTRA
14836
void* wolfSSL_CTX_get_ex_data(const WOLFSSL_CTX* ctx, int idx)
14837
0
{
14838
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_ex_data");
14839
0
#ifdef HAVE_EX_DATA
14840
0
    if (ctx != NULL) {
14841
0
        return wolfSSL_CRYPTO_get_ex_data(&ctx->ex_data, idx);
14842
0
    }
14843
#else
14844
    (void)ctx;
14845
    (void)idx;
14846
#endif
14847
0
    return NULL;
14848
0
}
14849
14850
int wolfSSL_CTX_set_ex_data(WOLFSSL_CTX* ctx, int idx, void* data)
14851
0
{
14852
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_ex_data");
14853
0
#ifdef HAVE_EX_DATA
14854
0
    if (ctx != NULL) {
14855
0
        return wolfSSL_CRYPTO_set_ex_data(&ctx->ex_data, idx, data);
14856
0
    }
14857
#else
14858
    (void)ctx;
14859
    (void)idx;
14860
    (void)data;
14861
#endif
14862
0
    return WOLFSSL_FAILURE;
14863
0
}
14864
14865
#ifdef HAVE_EX_DATA_CLEANUP_HOOKS
14866
int wolfSSL_CTX_set_ex_data_with_cleanup(
14867
    WOLFSSL_CTX* ctx,
14868
    int idx,
14869
    void* data,
14870
    wolfSSL_ex_data_cleanup_routine_t cleanup_routine)
14871
{
14872
    WOLFSSL_ENTER("wolfSSL_CTX_set_ex_data_with_cleanup");
14873
    if (ctx != NULL) {
14874
        return wolfSSL_CRYPTO_set_ex_data_with_cleanup(&ctx->ex_data, idx, data,
14875
                                                       cleanup_routine);
14876
    }
14877
    return WOLFSSL_FAILURE;
14878
}
14879
#endif /* HAVE_EX_DATA_CLEANUP_HOOKS */
14880
#endif /* OPENSSL_EXTRA */
14881
14882
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
14883
14884
/* Returns char* to app data stored in ex[0].
14885
 *
14886
 * ssl WOLFSSL structure to get app data from
14887
 */
14888
void* wolfSSL_get_app_data(const WOLFSSL *ssl)
14889
0
{
14890
    /* checkout exdata stuff... */
14891
0
    WOLFSSL_ENTER("wolfSSL_get_app_data");
14892
14893
0
    return wolfSSL_get_ex_data(ssl, 0);
14894
0
}
14895
14896
14897
/* Set ex array 0 to have app data
14898
 *
14899
 * ssl WOLFSSL struct to set app data in
14900
 * arg data to be stored
14901
 *
14902
 * Returns WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE on failure
14903
 */
14904
0
int wolfSSL_set_app_data(WOLFSSL *ssl, void* arg) {
14905
0
    WOLFSSL_ENTER("wolfSSL_set_app_data");
14906
14907
0
    return wolfSSL_set_ex_data(ssl, 0, arg);
14908
0
}
14909
14910
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
14911
14912
int wolfSSL_set_ex_data(WOLFSSL* ssl, int idx, void* data)
14913
0
{
14914
0
    WOLFSSL_ENTER("wolfSSL_set_ex_data");
14915
0
#ifdef HAVE_EX_DATA
14916
0
    if (ssl != NULL) {
14917
0
        return wolfSSL_CRYPTO_set_ex_data(&ssl->ex_data, idx, data);
14918
0
    }
14919
#else
14920
    WOLFSSL_MSG("HAVE_EX_DATA macro is not defined");
14921
    (void)ssl;
14922
    (void)idx;
14923
    (void)data;
14924
#endif
14925
0
    return WOLFSSL_FAILURE;
14926
0
}
14927
14928
#ifdef HAVE_EX_DATA_CLEANUP_HOOKS
14929
int wolfSSL_set_ex_data_with_cleanup(
14930
    WOLFSSL* ssl,
14931
    int idx,
14932
    void* data,
14933
    wolfSSL_ex_data_cleanup_routine_t cleanup_routine)
14934
{
14935
    WOLFSSL_ENTER("wolfSSL_set_ex_data_with_cleanup");
14936
    if (ssl != NULL)
14937
    {
14938
        return wolfSSL_CRYPTO_set_ex_data_with_cleanup(&ssl->ex_data, idx, data,
14939
                                                       cleanup_routine);
14940
    }
14941
    return WOLFSSL_FAILURE;
14942
}
14943
#endif /* HAVE_EX_DATA_CLEANUP_HOOKS */
14944
14945
void* wolfSSL_get_ex_data(const WOLFSSL* ssl, int idx)
14946
0
{
14947
0
    WOLFSSL_ENTER("wolfSSL_get_ex_data");
14948
0
#ifdef HAVE_EX_DATA
14949
0
    if (ssl != NULL) {
14950
0
        return wolfSSL_CRYPTO_get_ex_data(&ssl->ex_data, idx);
14951
0
    }
14952
#else
14953
    WOLFSSL_MSG("HAVE_EX_DATA macro is not defined");
14954
    (void)ssl;
14955
    (void)idx;
14956
#endif
14957
0
    return 0;
14958
0
}
14959
14960
#if defined(HAVE_LIGHTY) || defined(HAVE_STUNNEL) \
14961
    || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(OPENSSL_EXTRA)
14962
14963
/* returns the enum value associated with handshake state
14964
 *
14965
 * ssl the WOLFSSL structure to get state of
14966
 */
14967
int wolfSSL_get_state(const WOLFSSL* ssl)
14968
0
{
14969
0
    WOLFSSL_ENTER("wolfSSL_get_state");
14970
14971
0
    if (ssl == NULL) {
14972
0
        WOLFSSL_MSG("Null argument passed in");
14973
0
        return WOLFSSL_FAILURE;
14974
0
    }
14975
14976
0
    return ssl->options.handShakeState;
14977
0
}
14978
#endif /* HAVE_LIGHTY || HAVE_STUNNEL || WOLFSSL_MYSQL_COMPATIBLE */
14979
14980
#ifdef OPENSSL_EXTRA
14981
void wolfSSL_certs_clear(WOLFSSL* ssl)
14982
0
{
14983
0
    WOLFSSL_ENTER("wolfSSL_certs_clear");
14984
14985
0
    if (ssl == NULL)
14986
0
        return;
14987
14988
    /* ctx still owns certificate, certChain, key, dh, and cm */
14989
0
    if (ssl->buffers.weOwnCert) {
14990
0
        FreeDer(&ssl->buffers.certificate);
14991
0
        ssl->buffers.weOwnCert = 0;
14992
0
    }
14993
0
    ssl->buffers.certificate = NULL;
14994
0
    if (ssl->buffers.weOwnCertChain) {
14995
0
        FreeDer(&ssl->buffers.certChain);
14996
0
        ssl->buffers.weOwnCertChain = 0;
14997
0
    }
14998
0
    ssl->buffers.certChain = NULL;
14999
0
#ifdef WOLFSSL_TLS13
15000
0
    ssl->buffers.certChainCnt = 0;
15001
0
#endif
15002
0
    if (ssl->buffers.weOwnKey) {
15003
0
        FreeDer(&ssl->buffers.key);
15004
    #ifdef WOLFSSL_BLIND_PRIVATE_KEY
15005
        FreeDer(&ssl->buffers.keyMask);
15006
    #endif
15007
0
        ssl->buffers.weOwnKey = 0;
15008
0
    }
15009
0
    ssl->buffers.key      = NULL;
15010
#ifdef WOLFSSL_BLIND_PRIVATE_KEY
15011
    ssl->buffers.keyMask  = NULL;
15012
#endif
15013
0
    ssl->buffers.keyType  = 0;
15014
0
    ssl->buffers.keyId    = 0;
15015
0
    ssl->buffers.keyLabel = 0;
15016
0
    ssl->buffers.keySz    = 0;
15017
0
    ssl->buffers.keyDevId = 0;
15018
#ifdef WOLFSSL_DUAL_ALG_CERTS
15019
    if (ssl->buffers.weOwnAltKey) {
15020
        FreeDer(&ssl->buffers.altKey);
15021
    #ifdef WOLFSSL_BLIND_PRIVATE_KEY
15022
        FreeDer(&ssl->buffers.altKeyMask);
15023
    #endif
15024
        ssl->buffers.weOwnAltKey = 0;
15025
    }
15026
    ssl->buffers.altKey     = NULL;
15027
#ifdef WOLFSSL_BLIND_PRIVATE_KEY
15028
    ssl->buffers.altKeyMask = NULL;
15029
#endif
15030
#endif /* WOLFSSL_DUAL_ALG_CERTS */
15031
0
}
15032
#endif
15033
15034
#if defined(OPENSSL_ALL) || defined(WOLFSSL_ASIO) || defined(WOLFSSL_HAPROXY) \
15035
    || defined(WOLFSSL_NGINX) || defined(WOLFSSL_QT)
15036
15037
long wolfSSL_ctrl(WOLFSSL* ssl, int cmd, long opt, void* pt)
15038
0
{
15039
0
    WOLFSSL_ENTER("wolfSSL_ctrl");
15040
0
    if (ssl == NULL)
15041
0
        return BAD_FUNC_ARG;
15042
15043
0
    switch (cmd) {
15044
0
        #if defined(WOLFSSL_NGINX) || defined(WOLFSSL_QT) || \
15045
0
            defined(OPENSSL_ALL)
15046
0
        #ifdef HAVE_SNI
15047
0
        case SSL_CTRL_SET_TLSEXT_HOSTNAME:
15048
0
            WOLFSSL_MSG("Entering Case: SSL_CTRL_SET_TLSEXT_HOSTNAME.");
15049
0
            if (pt == NULL) {
15050
0
                WOLFSSL_MSG("Passed in NULL Host Name.");
15051
0
                break;
15052
0
            }
15053
0
            return wolfSSL_set_tlsext_host_name(ssl, (const char*) pt);
15054
0
        #endif /* HAVE_SNI */
15055
0
        #endif /* WOLFSSL_NGINX || WOLFSSL_QT || OPENSSL_ALL */
15056
0
        default:
15057
0
            WOLFSSL_MSG("Case not implemented.");
15058
0
    }
15059
0
    (void)opt;
15060
0
    (void)pt;
15061
0
    return WOLFSSL_FAILURE;
15062
0
}
15063
15064
long wolfSSL_CTX_ctrl(WOLFSSL_CTX* ctx, int cmd, long opt, void* pt)
15065
0
{
15066
0
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
15067
0
    long ctrl_opt;
15068
0
#endif
15069
0
    long ret = WOLFSSL_SUCCESS;
15070
15071
0
    WOLFSSL_ENTER("wolfSSL_CTX_ctrl");
15072
0
    if (ctx == NULL)
15073
0
        return WOLFSSL_FAILURE;
15074
15075
0
    switch (cmd) {
15076
0
    case SSL_CTRL_CHAIN:
15077
#ifdef SESSION_CERTS
15078
    {
15079
        /*
15080
         * We don't care about opt here because a copy of the certificate is
15081
         * stored anyway so increasing the reference counter is not necessary.
15082
         * Just check to make sure that it is set to one of the correct values.
15083
         */
15084
        WOLF_STACK_OF(WOLFSSL_X509)* sk = (WOLF_STACK_OF(WOLFSSL_X509)*) pt;
15085
        WOLFSSL_X509* x509;
15086
        int i;
15087
        if (opt != 0 && opt != 1) {
15088
            ret = WOLFSSL_FAILURE;
15089
            break;
15090
        }
15091
        /* Clear certificate chain */
15092
        FreeDer(&ctx->certChain);
15093
        if (sk) {
15094
            for (i = 0; i < wolfSSL_sk_X509_num(sk); i++) {
15095
                x509 = wolfSSL_sk_X509_value(sk, i);
15096
                /* Prevent wolfSSL_CTX_add_extra_chain_cert from freeing cert */
15097
                if (wolfSSL_X509_up_ref(x509) != 1) {
15098
                    WOLFSSL_MSG("Error increasing reference count");
15099
                    continue;
15100
                }
15101
                if (wolfSSL_CTX_add_extra_chain_cert(ctx, x509) !=
15102
                        WOLFSSL_SUCCESS) {
15103
                    WOLFSSL_MSG("Error adding certificate to context");
15104
                    /* Decrease reference count on failure */
15105
                    wolfSSL_X509_free(x509);
15106
                    x509 = NULL;
15107
                }
15108
            }
15109
        }
15110
        /* Free previous chain */
15111
        wolfSSL_sk_X509_pop_free(ctx->x509Chain, NULL);
15112
        ctx->x509Chain = sk;
15113
        if (sk && opt == 1) {
15114
            /* up all refs when opt == 1 */
15115
            for (i = 0; i < wolfSSL_sk_X509_num(sk); i++) {
15116
                x509 = wolfSSL_sk_X509_value(sk, i);
15117
                if (wolfSSL_X509_up_ref(x509) != 1) {
15118
                    WOLFSSL_MSG("Error increasing reference count");
15119
                    continue;
15120
                }
15121
            }
15122
        }
15123
    }
15124
#else
15125
0
        WOLFSSL_MSG("Session certificates not compiled in");
15126
0
        ret = WOLFSSL_FAILURE;
15127
0
#endif
15128
0
        break;
15129
15130
0
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
15131
0
    case SSL_CTRL_OPTIONS:
15132
0
        WOLFSSL_MSG("Entering Case: SSL_CTRL_OPTIONS.");
15133
0
        ctrl_opt = wolfSSL_CTX_set_options(ctx, opt);
15134
15135
        #ifdef WOLFSSL_QT
15136
        /* Set whether to use client or server cipher preference */
15137
        if ((ctrl_opt & WOLFSSL_OP_CIPHER_SERVER_PREFERENCE)
15138
                     == WOLFSSL_OP_CIPHER_SERVER_PREFERENCE) {
15139
            WOLFSSL_MSG("Using Server's Cipher Preference.");
15140
            ctx->useClientOrder = 0;
15141
        } else {
15142
            WOLFSSL_MSG("Using Client's Cipher Preference.");
15143
            ctx->useClientOrder = 1;
15144
        }
15145
        #endif /* WOLFSSL_QT */
15146
15147
0
        return ctrl_opt;
15148
0
#endif /* OPENSSL_EXTRA || HAVE_WEBSERVER */
15149
0
    case SSL_CTRL_EXTRA_CHAIN_CERT:
15150
0
        WOLFSSL_MSG("Entering Case: SSL_CTRL_EXTRA_CHAIN_CERT.");
15151
0
        if (pt == NULL) {
15152
0
            WOLFSSL_MSG("Passed in x509 pointer NULL.");
15153
0
            ret = WOLFSSL_FAILURE;
15154
0
            break;
15155
0
        }
15156
0
        return wolfSSL_CTX_add_extra_chain_cert(ctx, (WOLFSSL_X509*)pt);
15157
15158
0
#ifndef NO_DH
15159
0
    case SSL_CTRL_SET_TMP_DH:
15160
0
        WOLFSSL_MSG("Entering Case: SSL_CTRL_SET_TMP_DH.");
15161
0
        if (pt == NULL) {
15162
0
            WOLFSSL_MSG("Passed in DH pointer NULL.");
15163
0
            ret = WOLFSSL_FAILURE;
15164
0
            break;
15165
0
        }
15166
0
        return wolfSSL_CTX_set_tmp_dh(ctx, (WOLFSSL_DH*)pt);
15167
0
#endif
15168
15169
0
#ifdef HAVE_ECC
15170
0
    case SSL_CTRL_SET_TMP_ECDH:
15171
0
        WOLFSSL_MSG("Entering Case: SSL_CTRL_SET_TMP_ECDH.");
15172
0
        if (pt == NULL) {
15173
0
            WOLFSSL_MSG("Passed in ECDH pointer NULL.");
15174
0
            ret = WOLFSSL_FAILURE;
15175
0
            break;
15176
0
        }
15177
0
        return wolfSSL_SSL_CTX_set_tmp_ecdh(ctx, (WOLFSSL_EC_KEY*)pt);
15178
0
#endif
15179
0
    case SSL_CTRL_MODE:
15180
0
        wolfSSL_CTX_set_mode(ctx,opt);
15181
0
        break;
15182
0
    case SSL_CTRL_SET_MIN_PROTO_VERSION:
15183
0
        WOLFSSL_MSG("set min proto version");
15184
0
        return wolfSSL_CTX_set_min_proto_version(ctx, (int)opt);
15185
0
    case SSL_CTRL_SET_MAX_PROTO_VERSION:
15186
0
        WOLFSSL_MSG("set max proto version");
15187
0
        return wolfSSL_CTX_set_max_proto_version(ctx, (int)opt);
15188
0
    case SSL_CTRL_GET_MIN_PROTO_VERSION:
15189
0
        WOLFSSL_MSG("get min proto version");
15190
0
        return wolfSSL_CTX_get_min_proto_version(ctx);
15191
0
    case SSL_CTRL_GET_MAX_PROTO_VERSION:
15192
0
        WOLFSSL_MSG("get max proto version");
15193
0
        return wolfSSL_CTX_get_max_proto_version(ctx);
15194
0
    default:
15195
0
        WOLFSSL_MSG("CTX_ctrl cmd not implemented");
15196
0
        ret = WOLFSSL_FAILURE;
15197
0
        break;
15198
0
    }
15199
15200
0
    (void)ctx;
15201
0
    (void)cmd;
15202
0
    (void)opt;
15203
0
    (void)pt;
15204
0
    WOLFSSL_LEAVE("wolfSSL_CTX_ctrl", (int)ret);
15205
0
    return ret;
15206
0
}
15207
15208
#ifndef NO_WOLFSSL_STUB
15209
long wolfSSL_CTX_callback_ctrl(WOLFSSL_CTX* ctx, int cmd, void (*fp)(void))
15210
0
{
15211
0
    (void) ctx;
15212
0
    (void) cmd;
15213
0
    (void) fp;
15214
0
    WOLFSSL_STUB("wolfSSL_CTX_callback_ctrl");
15215
0
    return WOLFSSL_FAILURE;
15216
15217
0
}
15218
#endif /* NO_WOLFSSL_STUB */
15219
15220
#ifndef NO_WOLFSSL_STUB
15221
long wolfSSL_CTX_clear_extra_chain_certs(WOLFSSL_CTX* ctx)
15222
0
{
15223
0
    return wolfSSL_CTX_ctrl(ctx, SSL_CTRL_CLEAR_EXTRA_CHAIN_CERTS, 0L, NULL);
15224
0
}
15225
#endif
15226
15227
/* Returns the verifyCallback from the ssl structure if successful.
15228
Returns NULL otherwise. */
15229
VerifyCallback wolfSSL_get_verify_callback(WOLFSSL* ssl)
15230
0
{
15231
0
    WOLFSSL_ENTER("wolfSSL_get_verify_callback");
15232
0
    if (ssl) {
15233
0
        return ssl->verifyCallback;
15234
0
    }
15235
0
    return NULL;
15236
0
}
15237
15238
#endif /* OPENSSL_ALL || WOLFSSL_ASIO || WOLFSSL_HAPROXY || WOLFSSL_QT */
15239
15240
15241
/* stunnel compatibility functions*/
15242
#if defined(OPENSSL_ALL) || (defined(OPENSSL_EXTRA) && \
15243
    (defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) || \
15244
     defined(HAVE_LIGHTY) || defined(WOLFSSL_HAPROXY) || \
15245
     defined(WOLFSSL_OPENSSH)))
15246
void wolfSSL_ERR_remove_thread_state(void* pid)
15247
0
{
15248
0
    (void) pid;
15249
0
    return;
15250
0
}
15251
15252
#ifndef NO_FILESYSTEM
15253
/***TBD ***/
15254
void wolfSSL_print_all_errors_fp(XFILE fp)
15255
0
{
15256
0
    (void)fp;
15257
0
}
15258
#endif /* !NO_FILESYSTEM */
15259
15260
#endif /* OPENSSL_ALL || OPENSSL_EXTRA || HAVE_STUNNEL || WOLFSSL_NGINX ||
15261
    HAVE_LIGHTY || WOLFSSL_HAPROXY || WOLFSSL_OPENSSH */
15262
15263
/* Note: This is a huge section of API's - through
15264
 *       wolfSSL_X509_OBJECT_get0_X509_CRL */
15265
#if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA)
15266
15267
#if defined(USE_WOLFSSL_MEMORY) && !defined(WOLFSSL_DEBUG_MEMORY) && \
15268
    !defined(WOLFSSL_STATIC_MEMORY)
15269
static wolfSSL_OSSL_Malloc_cb  ossl_malloc  = NULL;
15270
static wolfSSL_OSSL_Free_cb    ossl_free    = NULL;
15271
static wolfSSL_OSSL_Realloc_cb ossl_realloc = NULL;
15272
15273
static void* OSSL_Malloc(size_t size)
15274
0
{
15275
0
    if (ossl_malloc != NULL)
15276
0
        return ossl_malloc(size, NULL, 0);
15277
0
    else
15278
0
        return NULL;
15279
0
}
15280
15281
static void  OSSL_Free(void *ptr)
15282
0
{
15283
0
    if (ossl_free != NULL)
15284
0
        ossl_free(ptr, NULL, 0);
15285
0
}
15286
15287
static void* OSSL_Realloc(void *ptr, size_t size)
15288
0
{
15289
0
    if (ossl_realloc != NULL)
15290
0
        return ossl_realloc(ptr, size, NULL, 0);
15291
0
    else
15292
0
        return NULL;
15293
0
}
15294
#endif /* USE_WOLFSSL_MEMORY && !WOLFSSL_DEBUG_MEMORY &&
15295
        * !WOLFSSL_STATIC_MEMORY */
15296
15297
int wolfSSL_CRYPTO_set_mem_functions(
15298
        wolfSSL_OSSL_Malloc_cb  m,
15299
        wolfSSL_OSSL_Realloc_cb r,
15300
        wolfSSL_OSSL_Free_cb    f)
15301
0
{
15302
0
#if defined(USE_WOLFSSL_MEMORY) && !defined(WOLFSSL_STATIC_MEMORY)
15303
#ifdef WOLFSSL_DEBUG_MEMORY
15304
    WOLFSSL_MSG("mem functions will receive function name instead of "
15305
                "file name");
15306
    if (wolfSSL_SetAllocators((wolfSSL_Malloc_cb)m, (wolfSSL_Free_cb)f,
15307
            (wolfSSL_Realloc_cb)r) == 0)
15308
        return WOLFSSL_SUCCESS;
15309
#else
15310
0
    WOLFSSL_MSG("wolfSSL was compiled without WOLFSSL_DEBUG_MEMORY mem "
15311
0
                "functions will receive a NULL file name and 0 for the "
15312
0
                "line number.");
15313
0
    if (wolfSSL_SetAllocators((wolfSSL_Malloc_cb)OSSL_Malloc,
15314
0
           (wolfSSL_Free_cb)OSSL_Free, (wolfSSL_Realloc_cb)OSSL_Realloc) == 0) {
15315
0
        ossl_malloc = m;
15316
0
        ossl_free = f;
15317
0
        ossl_realloc = r;
15318
0
        return WOLFSSL_SUCCESS;
15319
0
    }
15320
0
#endif
15321
0
    else
15322
0
        return WOLFSSL_FAILURE;
15323
#else
15324
    (void)m;
15325
    (void)r;
15326
    (void)f;
15327
    WOLFSSL_MSG("wolfSSL allocator callback functions not compiled in");
15328
    return WOLFSSL_FAILURE;
15329
#endif
15330
0
}
15331
15332
int wolfSSL_ERR_load_ERR_strings(void)
15333
0
{
15334
0
    return WOLFSSL_SUCCESS;
15335
0
}
15336
15337
void wolfSSL_ERR_load_crypto_strings(void)
15338
0
{
15339
0
    WOLFSSL_ENTER("wolfSSL_ERR_load_crypto_strings");
15340
    /* Do nothing */
15341
0
    return;
15342
0
}
15343
15344
int wolfSSL_FIPS_mode(void)
15345
0
{
15346
#ifdef HAVE_FIPS
15347
    return 1;
15348
#else
15349
0
    return 0;
15350
0
#endif
15351
0
}
15352
15353
int wolfSSL_FIPS_mode_set(int r)
15354
0
{
15355
#ifdef HAVE_FIPS
15356
    if (r == 0) {
15357
        WOLFSSL_MSG("Cannot disable FIPS at runtime.");
15358
        return WOLFSSL_FAILURE;
15359
    }
15360
    return WOLFSSL_SUCCESS;
15361
#else
15362
0
    if (r == 0) {
15363
0
        return WOLFSSL_SUCCESS;
15364
0
    }
15365
0
    WOLFSSL_MSG("Cannot enable FIPS. This isn't the wolfSSL FIPS code.");
15366
0
    return WOLFSSL_FAILURE;
15367
0
#endif
15368
0
}
15369
15370
int wolfSSL_CIPHER_get_bits(const WOLFSSL_CIPHER *c, int *alg_bits)
15371
0
{
15372
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
15373
0
    WOLFSSL_ENTER("wolfSSL_CIPHER_get_bits");
15374
15375
0
    #if defined(WOLFSSL_QT) || defined(OPENSSL_ALL)
15376
0
    (void)alg_bits;
15377
0
    if (c!= NULL)
15378
0
        ret = c->bits;
15379
    #else
15380
    if (c != NULL && c->ssl != NULL) {
15381
        ret = 8 * c->ssl->specs.key_size;
15382
        if (alg_bits != NULL) {
15383
            *alg_bits = ret;
15384
        }
15385
    }
15386
    #endif
15387
0
    return ret;
15388
0
}
15389
15390
#ifdef HAVE_SNI
15391
int wolfSSL_set_tlsext_host_name(WOLFSSL* ssl, const char* host_name)
15392
0
{
15393
0
    int ret;
15394
0
    WOLFSSL_ENTER("wolfSSL_set_tlsext_host_name");
15395
0
    ret = wolfSSL_UseSNI(ssl, WOLFSSL_SNI_HOST_NAME,
15396
0
            host_name, (word16)XSTRLEN(host_name));
15397
0
    WOLFSSL_LEAVE("wolfSSL_set_tlsext_host_name", ret);
15398
0
    return ret;
15399
0
}
15400
15401
#ifndef NO_WOLFSSL_SERVER
15402
/* May be called by server to get the requested accepted name and by the client
15403
 * to get the requested name. */
15404
const char * wolfSSL_get_servername(WOLFSSL* ssl, byte type)
15405
0
{
15406
0
    void * serverName = NULL;
15407
0
    if (ssl == NULL)
15408
0
        return NULL;
15409
0
    TLSX_SNI_GetRequest(ssl->extensions, type, &serverName,
15410
0
            !wolfSSL_is_server(ssl));
15411
0
    return (const char *)serverName;
15412
0
}
15413
#endif
15414
15415
#endif /* HAVE_SNI */
15416
15417
WOLFSSL_CTX* wolfSSL_set_SSL_CTX(WOLFSSL* ssl, WOLFSSL_CTX* ctx)
15418
0
{
15419
0
    int ret;
15420
    /* This method requires some explanation. Its sibling is
15421
     *   int SetSSL_CTX(WOLFSSL* ssl, WOLFSSL_CTX* ctx, int writeDup)
15422
     * which re-inits the WOLFSSL* with all settings in the new CTX.
15423
     * That one is the right one to use *before* a handshake is started.
15424
     *
15425
     * This method was added by OpenSSL to be used *during* the handshake, e.g.
15426
     * when a server inspects the SNI in a ClientHello callback and
15427
     * decides which set of certificates to use.
15428
     *
15429
     * Since, at the time the SNI callback is run, some decisions on
15430
     * Extensions or the ServerHello might already have been taken, this
15431
     * method is very restricted in what it does:
15432
     * - changing the server certificate(s)
15433
     * - changing the server id for session handling
15434
     * and everything else in WOLFSSL* needs to remain untouched.
15435
     */
15436
0
    WOLFSSL_ENTER("wolfSSL_set_SSL_CTX");
15437
0
    if (ssl == NULL || ctx == NULL)
15438
0
        return NULL;
15439
0
    if (ssl->ctx == ctx)
15440
0
        return ssl->ctx;
15441
15442
0
    if (ctx->suites == NULL) {
15443
        /* suites */
15444
0
        if (AllocateCtxSuites(ctx) != 0)
15445
0
            return NULL;
15446
0
        InitSSL_CTX_Suites(ctx);
15447
0
    }
15448
15449
0
    wolfSSL_RefWithMutexInc(&ctx->ref, &ret);
15450
#ifdef WOLFSSL_REFCNT_ERROR_RETURN
15451
    if (ret != 0) {
15452
        /* can only fail on serious stuff, like mutex not working
15453
         * or ctx refcount out of whack. */
15454
        return NULL;
15455
    }
15456
#else
15457
0
    (void)ret;
15458
0
#endif
15459
0
    if (ssl->ctx != NULL)
15460
0
        wolfSSL_CTX_free(ssl->ctx);
15461
0
    ssl->ctx = ctx;
15462
15463
0
#ifndef NO_CERTS
15464
0
#ifdef WOLFSSL_COPY_CERT
15465
    /* If WOLFSSL_COPY_CERT defined, always make new copy of cert from ctx */
15466
0
    if (ctx->certificate != NULL) {
15467
0
        if (ssl->buffers.certificate != NULL) {
15468
0
            FreeDer(&ssl->buffers.certificate);
15469
0
            ssl->buffers.certificate = NULL;
15470
0
        }
15471
0
        ret = AllocCopyDer(&ssl->buffers.certificate, ctx->certificate->buffer,
15472
0
            ctx->certificate->length, ctx->certificate->type,
15473
0
            ctx->certificate->heap);
15474
0
        if (ret != 0) {
15475
0
            ssl->buffers.weOwnCert = 0;
15476
0
            return NULL;
15477
0
        }
15478
15479
0
        ssl->buffers.weOwnCert = 1;
15480
0
    }
15481
0
    if (ctx->certChain != NULL) {
15482
0
        if (ssl->buffers.certChain != NULL) {
15483
0
            FreeDer(&ssl->buffers.certChain);
15484
0
            ssl->buffers.certChain = NULL;
15485
0
        }
15486
0
        ret = AllocCopyDer(&ssl->buffers.certChain, ctx->certChain->buffer,
15487
0
            ctx->certChain->length, ctx->certChain->type,
15488
0
            ctx->certChain->heap);
15489
0
        if (ret != 0) {
15490
0
            ssl->buffers.weOwnCertChain = 0;
15491
0
            return NULL;
15492
0
        }
15493
15494
0
        ssl->buffers.weOwnCertChain = 1;
15495
0
    }
15496
#else
15497
    /* ctx owns certificate, certChain and key */
15498
    ssl->buffers.certificate = ctx->certificate;
15499
    ssl->buffers.certChain = ctx->certChain;
15500
#endif
15501
0
#ifdef WOLFSSL_TLS13
15502
0
    ssl->buffers.certChainCnt = ctx->certChainCnt;
15503
0
#endif
15504
0
#ifndef WOLFSSL_BLIND_PRIVATE_KEY
15505
0
#ifdef WOLFSSL_COPY_KEY
15506
0
    if (ctx->privateKey != NULL) {
15507
0
        if (ssl->buffers.key != NULL) {
15508
0
            FreeDer(&ssl->buffers.key);
15509
0
            ssl->buffers.key = NULL;
15510
0
        }
15511
0
        ret = AllocCopyDer(&ssl->buffers.key, ctx->privateKey->buffer,
15512
0
            ctx->privateKey->length, ctx->privateKey->type,
15513
0
            ctx->privateKey->heap);
15514
0
        if (ret != 0) {
15515
0
            ssl->buffers.weOwnKey = 0;
15516
0
            return NULL;
15517
0
        }
15518
0
        ssl->buffers.weOwnKey = 1;
15519
0
    }
15520
0
    else {
15521
0
        ssl->buffers.key      = ctx->privateKey;
15522
0
    }
15523
#else
15524
    ssl->buffers.key      = ctx->privateKey;
15525
#endif
15526
#else
15527
    if (ctx->privateKey != NULL) {
15528
        ret = AllocCopyDer(&ssl->buffers.key, ctx->privateKey->buffer,
15529
            ctx->privateKey->length, ctx->privateKey->type,
15530
            ctx->privateKey->heap);
15531
        if (ret != 0) {
15532
            return NULL;
15533
        }
15534
        /* Blind the private key for the SSL with new random mask. */
15535
        wolfssl_priv_der_blind_toggle(ssl->buffers.key, ctx->privateKeyMask);
15536
        ret = wolfssl_priv_der_blind(ssl->rng, ssl->buffers.key,
15537
            &ssl->buffers.keyMask);
15538
        if (ret != 0) {
15539
            return NULL;
15540
        }
15541
    }
15542
#endif
15543
0
    ssl->buffers.keyType  = ctx->privateKeyType;
15544
0
    ssl->buffers.keyId    = ctx->privateKeyId;
15545
0
    ssl->buffers.keyLabel = ctx->privateKeyLabel;
15546
0
    ssl->buffers.keySz    = ctx->privateKeySz;
15547
0
    ssl->buffers.keyDevId = ctx->privateKeyDevId;
15548
    /* flags indicating what certs/keys are available */
15549
0
    ssl->options.haveRSA          = ctx->haveRSA;
15550
0
    ssl->options.haveDH           = ctx->haveDH;
15551
0
    ssl->options.haveECDSAsig     = ctx->haveECDSAsig;
15552
0
    ssl->options.haveECC          = ctx->haveECC;
15553
0
    ssl->options.haveStaticECC    = ctx->haveStaticECC;
15554
0
    ssl->options.haveFalconSig    = ctx->haveFalconSig;
15555
0
    ssl->options.haveDilithiumSig = ctx->haveDilithiumSig;
15556
#ifdef WOLFSSL_DUAL_ALG_CERTS
15557
#ifndef WOLFSSL_BLIND_PRIVATE_KEY
15558
    ssl->buffers.altKey   = ctx->altPrivateKey;
15559
#else
15560
    if (ctx->altPrivateKey != NULL) {
15561
        ret = AllocCopyDer(&ssl->buffers.altKey, ctx->altPrivateKey->buffer,
15562
            ctx->altPrivateKey->length, ctx->altPrivateKey->type,
15563
            ctx->altPrivateKey->heap);
15564
        if (ret != 0) {
15565
            return NULL;
15566
        }
15567
        /* Blind the private key for the SSL with new random mask. */
15568
        wolfssl_priv_der_blind_toggle(ssl->buffers.altKey,
15569
                                      ctx->altPrivateKeyMask);
15570
        ret = wolfssl_priv_der_blind(ssl->rng, ssl->buffers.altKey,
15571
            &ssl->buffers.altKeyMask);
15572
        if (ret != 0) {
15573
            return NULL;
15574
        }
15575
    }
15576
#endif
15577
    ssl->buffers.altKeySz   = ctx->altPrivateKeySz;
15578
    ssl->buffers.altKeyType = ctx->altPrivateKeyType;
15579
#endif /* WOLFSSL_DUAL_ALG_CERTS */
15580
0
#endif
15581
15582
0
#ifdef WOLFSSL_SESSION_ID_CTX
15583
    /* copy over application session context ID */
15584
0
    ssl->sessionCtxSz = ctx->sessionCtxSz;
15585
0
    XMEMCPY(ssl->sessionCtx, ctx->sessionCtx, ctx->sessionCtxSz);
15586
0
#endif
15587
15588
0
    return ssl->ctx;
15589
0
}
15590
15591
15592
VerifyCallback wolfSSL_CTX_get_verify_callback(WOLFSSL_CTX* ctx)
15593
0
{
15594
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_verify_callback");
15595
0
    if(ctx)
15596
0
        return ctx->verifyCallback;
15597
0
    return NULL;
15598
0
}
15599
15600
#ifdef HAVE_SNI
15601
/* this is a compatibility function, consider using
15602
 * wolfSSL_CTX_set_servername_callback */
15603
int wolfSSL_CTX_set_tlsext_servername_callback(WOLFSSL_CTX* ctx,
15604
                                               CallbackSniRecv cb)
15605
0
{
15606
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_tlsext_servername_callback");
15607
0
    if (ctx) {
15608
0
        ctx->sniRecvCb = cb;
15609
0
        return WOLFSSL_SUCCESS;
15610
0
    }
15611
0
    return WOLFSSL_FAILURE;
15612
0
}
15613
15614
#endif /* HAVE_SNI */
15615
15616
#ifndef NO_BIO
15617
0
void wolfSSL_ERR_load_BIO_strings(void) {
15618
0
    WOLFSSL_ENTER("wolfSSL_ERR_load_BIO_strings");
15619
    /* do nothing */
15620
0
}
15621
#endif
15622
15623
#ifndef NO_WOLFSSL_STUB
15624
/* Set THREADID callback, return 1 on success, 0 on error */
15625
int wolfSSL_THREADID_set_callback(
15626
        void(*threadid_func)(WOLFSSL_CRYPTO_THREADID*))
15627
0
{
15628
0
    WOLFSSL_ENTER("wolfSSL_THREADID_set_callback");
15629
0
    WOLFSSL_STUB("CRYPTO_THREADID_set_callback");
15630
0
    (void)threadid_func;
15631
0
    return 1;
15632
0
}
15633
#endif
15634
15635
#ifndef NO_WOLFSSL_STUB
15636
void wolfSSL_THREADID_set_numeric(void* id, unsigned long val)
15637
0
{
15638
0
    WOLFSSL_ENTER("wolfSSL_THREADID_set_numeric");
15639
0
    WOLFSSL_STUB("CRYPTO_THREADID_set_numeric");
15640
0
    (void)id;
15641
0
    (void)val;
15642
0
    return;
15643
0
}
15644
#endif
15645
15646
#endif /* OPENSSL_ALL || OPENSSL_EXTRA */
15647
15648
#ifdef HAVE_SNI
15649
15650
void wolfSSL_CTX_set_servername_callback(WOLFSSL_CTX* ctx, CallbackSniRecv cb)
15651
0
{
15652
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_servername_callback");
15653
0
    if (ctx)
15654
0
        ctx->sniRecvCb = cb;
15655
0
}
15656
15657
15658
int wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX* ctx, void* arg)
15659
0
{
15660
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_servername_arg");
15661
0
    if (ctx) {
15662
0
        ctx->sniRecvCbArg = arg;
15663
0
        return WOLFSSL_SUCCESS;
15664
0
    }
15665
0
    return WOLFSSL_FAILURE;
15666
0
}
15667
15668
#endif /* HAVE_SNI */
15669
15670
#if defined(OPENSSL_EXTRA)
15671
15672
int wolfSSL_CRYPTO_memcmp(const void *a, const void *b, size_t size)
15673
0
{
15674
0
    if (!a || !b)
15675
0
        return 0;
15676
0
    return ConstantCompare((const byte*)a, (const byte*)b, (int)size);
15677
0
}
15678
15679
unsigned long wolfSSL_ERR_peek_last_error(void)
15680
0
{
15681
0
    WOLFSSL_ENTER("wolfSSL_ERR_peek_last_error");
15682
15683
0
#ifdef WOLFSSL_HAVE_ERROR_QUEUE
15684
0
    {
15685
0
        int ret;
15686
15687
0
        if ((ret = wc_PeekErrorNode(-1, NULL, NULL, NULL)) < 0) {
15688
0
            WOLFSSL_MSG("Issue peeking at error node in queue");
15689
0
            return 0;
15690
0
        }
15691
0
        if (ret == -WC_NO_ERR_TRACE(ASN_NO_PEM_HEADER))
15692
0
            return (WOLFSSL_ERR_LIB_PEM << 24) | -WC_NO_ERR_TRACE(WOLFSSL_PEM_R_NO_START_LINE_E);
15693
    #if defined(WOLFSSL_PYTHON)
15694
        if (ret == ASN1_R_HEADER_TOO_LONG)
15695
            return (WOLFSSL_ERR_LIB_ASN1 << 24) | -WC_NO_ERR_TRACE(WOLFSSL_ASN1_R_HEADER_TOO_LONG_E);
15696
    #endif
15697
0
        return (unsigned long)ret;
15698
0
    }
15699
#else
15700
    return (unsigned long)(0 - NOT_COMPILED_IN);
15701
#endif
15702
0
}
15703
15704
#endif /* OPENSSL_EXTRA */
15705
15706
int wolfSSL_version(WOLFSSL* ssl)
15707
0
{
15708
0
    WOLFSSL_ENTER("wolfSSL_version");
15709
0
    if (ssl->version.major == SSLv3_MAJOR) {
15710
0
        switch (ssl->version.minor) {
15711
0
            case SSLv3_MINOR :
15712
0
                return SSL3_VERSION;
15713
0
            case TLSv1_MINOR :
15714
0
                return TLS1_VERSION;
15715
0
            case TLSv1_1_MINOR :
15716
0
                return TLS1_1_VERSION;
15717
0
            case TLSv1_2_MINOR :
15718
0
                return TLS1_2_VERSION;
15719
0
            case TLSv1_3_MINOR :
15720
0
                return TLS1_3_VERSION;
15721
0
            default:
15722
0
                return WOLFSSL_FAILURE;
15723
0
        }
15724
0
    }
15725
0
    else if (ssl->version.major == DTLS_MAJOR) {
15726
0
        switch (ssl->version.minor) {
15727
0
            case DTLS_MINOR :
15728
0
                return DTLS1_VERSION;
15729
0
            case DTLSv1_2_MINOR :
15730
0
                return DTLS1_2_VERSION;
15731
0
            case DTLSv1_3_MINOR:
15732
0
                return DTLS1_3_VERSION;
15733
0
            default:
15734
0
                return WOLFSSL_FAILURE;
15735
0
        }
15736
0
    }
15737
0
    return WOLFSSL_FAILURE;
15738
0
}
15739
15740
WOLFSSL_CTX* wolfSSL_get_SSL_CTX(const WOLFSSL* ssl)
15741
0
{
15742
0
    WOLFSSL_ENTER("wolfSSL_get_SSL_CTX");
15743
0
    return ssl->ctx;
15744
0
}
15745
15746
#if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA) || defined(HAVE_STUNNEL) || \
15747
    defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX)
15748
15749
/* TODO: Doesn't currently track SSL_VERIFY_CLIENT_ONCE */
15750
int wolfSSL_get_verify_mode(const WOLFSSL* ssl)
15751
0
{
15752
0
    int mode = 0;
15753
0
    WOLFSSL_ENTER("wolfSSL_get_verify_mode");
15754
15755
0
    if (!ssl) {
15756
0
        return WOLFSSL_FAILURE;
15757
0
    }
15758
15759
0
    if (ssl->options.verifyNone) {
15760
0
        mode = WOLFSSL_VERIFY_NONE;
15761
0
    }
15762
0
    else {
15763
0
        if (ssl->options.verifyPeer) {
15764
0
            mode |= WOLFSSL_VERIFY_PEER;
15765
0
        }
15766
0
        if (ssl->options.failNoCert) {
15767
0
            mode |= WOLFSSL_VERIFY_FAIL_IF_NO_PEER_CERT;
15768
0
        }
15769
0
        if (ssl->options.failNoCertxPSK) {
15770
0
            mode |= WOLFSSL_VERIFY_FAIL_EXCEPT_PSK;
15771
0
        }
15772
#if defined(WOLFSSL_TLS13) && defined(WOLFSSL_POST_HANDSHAKE_AUTH)
15773
        if (ssl->options.verifyPostHandshake) {
15774
            mode |= WOLFSSL_VERIFY_POST_HANDSHAKE;
15775
        }
15776
#endif
15777
0
    }
15778
15779
0
    WOLFSSL_LEAVE("wolfSSL_get_verify_mode", mode);
15780
0
    return mode;
15781
0
}
15782
15783
int wolfSSL_CTX_get_verify_mode(const WOLFSSL_CTX* ctx)
15784
0
{
15785
0
    int mode = 0;
15786
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_verify_mode");
15787
15788
0
    if (!ctx) {
15789
0
        return WOLFSSL_FAILURE;
15790
0
    }
15791
15792
0
    if (ctx->verifyNone) {
15793
0
        mode = WOLFSSL_VERIFY_NONE;
15794
0
    }
15795
0
    else {
15796
0
        if (ctx->verifyPeer) {
15797
0
            mode |= WOLFSSL_VERIFY_PEER;
15798
0
        }
15799
0
        if (ctx->failNoCert) {
15800
0
            mode |= WOLFSSL_VERIFY_FAIL_IF_NO_PEER_CERT;
15801
0
        }
15802
0
        if (ctx->failNoCertxPSK) {
15803
0
            mode |= WOLFSSL_VERIFY_FAIL_EXCEPT_PSK;
15804
0
        }
15805
#if defined(WOLFSSL_TLS13) && defined(WOLFSSL_POST_HANDSHAKE_AUTH)
15806
        if (ctx->verifyPostHandshake) {
15807
            mode |= WOLFSSL_VERIFY_POST_HANDSHAKE;
15808
        }
15809
#endif
15810
0
    }
15811
15812
0
    WOLFSSL_LEAVE("wolfSSL_CTX_get_verify_mode", mode);
15813
0
    return mode;
15814
0
}
15815
15816
#endif
15817
15818
#ifdef WOLFSSL_JNI
15819
15820
int wolfSSL_set_jobject(WOLFSSL* ssl, void* objPtr)
15821
{
15822
    WOLFSSL_ENTER("wolfSSL_set_jobject");
15823
    if (ssl != NULL)
15824
    {
15825
        ssl->jObjectRef = objPtr;
15826
        return WOLFSSL_SUCCESS;
15827
    }
15828
    return WOLFSSL_FAILURE;
15829
}
15830
15831
void* wolfSSL_get_jobject(WOLFSSL* ssl)
15832
{
15833
    WOLFSSL_ENTER("wolfSSL_get_jobject");
15834
    if (ssl != NULL)
15835
        return ssl->jObjectRef;
15836
    return NULL;
15837
}
15838
15839
#endif /* WOLFSSL_JNI */
15840
15841
15842
#ifdef WOLFSSL_ASYNC_CRYPT
15843
int wolfSSL_CTX_AsyncPoll(WOLFSSL_CTX* ctx, WOLF_EVENT** events, int maxEvents,
15844
    WOLF_EVENT_FLAG flags, int* eventCount)
15845
{
15846
    if (ctx == NULL) {
15847
        return BAD_FUNC_ARG;
15848
    }
15849
15850
    return wolfAsync_EventQueuePoll(&ctx->event_queue, NULL,
15851
                                        events, maxEvents, flags, eventCount);
15852
}
15853
15854
int wolfSSL_AsyncPoll(WOLFSSL* ssl, WOLF_EVENT_FLAG flags)
15855
{
15856
    int ret, eventCount = 0;
15857
    WOLF_EVENT* events[1];
15858
15859
    if (ssl == NULL) {
15860
        return BAD_FUNC_ARG;
15861
    }
15862
15863
    ret = wolfAsync_EventQueuePoll(&ssl->ctx->event_queue, ssl,
15864
        events, sizeof(events)/sizeof(events[0]), flags, &eventCount);
15865
    if (ret == 0) {
15866
        ret = eventCount;
15867
    }
15868
15869
    return ret;
15870
}
15871
#endif /* WOLFSSL_ASYNC_CRYPT */
15872
15873
#ifdef OPENSSL_EXTRA
15874
15875
static int peek_ignore_err(int err)
15876
0
{
15877
0
  switch(err) {
15878
0
    case -WC_NO_ERR_TRACE(WANT_READ):
15879
0
    case -WC_NO_ERR_TRACE(WANT_WRITE):
15880
0
    case -WC_NO_ERR_TRACE(ZERO_RETURN):
15881
0
    case -WOLFSSL_ERROR_ZERO_RETURN:
15882
0
    case -WC_NO_ERR_TRACE(SOCKET_PEER_CLOSED_E):
15883
0
    case -WC_NO_ERR_TRACE(SOCKET_ERROR_E):
15884
0
      return 1;
15885
0
    default:
15886
0
      return 0;
15887
0
  }
15888
0
}
15889
15890
unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line,
15891
                                               const char **data, int *flags)
15892
0
{
15893
0
  unsigned long err;
15894
15895
0
    WOLFSSL_ENTER("wolfSSL_ERR_peek_error_line_data");
15896
0
    err = wc_PeekErrorNodeLineData(file, line, data, flags, peek_ignore_err);
15897
15898
0
    if (err == -WC_NO_ERR_TRACE(ASN_NO_PEM_HEADER))
15899
0
        return (WOLFSSL_ERR_LIB_PEM << 24) | -WC_NO_ERR_TRACE(WOLFSSL_PEM_R_NO_START_LINE_E);
15900
0
#ifdef OPENSSL_ALL
15901
    /* PARSE_ERROR is returned if an HTTP request is detected. */
15902
0
    else if (err == -WC_NO_ERR_TRACE(PARSE_ERROR))
15903
0
        return (WOLFSSL_ERR_LIB_SSL << 24) | -WC_NO_ERR_TRACE(PARSE_ERROR) /* SSL_R_HTTP_REQUEST */;
15904
0
#endif
15905
#if defined(OPENSSL_ALL) && defined(WOLFSSL_PYTHON)
15906
    else if (err == ASN1_R_HEADER_TOO_LONG)
15907
        return (WOLFSSL_ERR_LIB_ASN1 << 24) | -WC_NO_ERR_TRACE(WOLFSSL_ASN1_R_HEADER_TOO_LONG_E);
15908
#endif
15909
0
  return err;
15910
0
}
15911
#endif
15912
15913
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL) || \
15914
    defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY)
15915
15916
#if !defined(WOLFSSL_USER_IO)
15917
/* converts an IPv6 or IPv4 address into an octet string for use with rfc3280
15918
 * example input would be "127.0.0.1" and the returned value would be 7F000001
15919
 */
15920
WOLFSSL_ASN1_STRING* wolfSSL_a2i_IPADDRESS(const char* ipa)
15921
0
{
15922
0
    int ipaSz = WOLFSSL_IP4_ADDR_LEN;
15923
0
    char buf[WOLFSSL_IP6_ADDR_LEN + 1]; /* plus 1 for terminator */
15924
0
    int  af = WOLFSSL_IP4;
15925
0
    WOLFSSL_ASN1_STRING *ret = NULL;
15926
15927
0
    if (ipa == NULL)
15928
0
        return NULL;
15929
15930
0
    if (XSTRSTR(ipa, ":") != NULL) {
15931
0
        af = WOLFSSL_IP6;
15932
0
        ipaSz = WOLFSSL_IP6_ADDR_LEN;
15933
0
    }
15934
15935
0
    buf[WOLFSSL_IP6_ADDR_LEN] = '\0';
15936
#ifdef FREESCALE_MQX
15937
    if (XINET_PTON(af, ipa, (void*)buf, sizeof(buf)) != RTCS_OK) {
15938
#else
15939
0
    if (XINET_PTON(af, ipa, (void*)buf) != 1) {
15940
0
#endif
15941
0
        WOLFSSL_MSG("Error parsing IP address");
15942
0
        return NULL;
15943
0
    }
15944
15945
0
    ret = wolfSSL_ASN1_STRING_new();
15946
0
    if (ret != NULL) {
15947
0
        if (wolfSSL_ASN1_STRING_set(ret, buf, ipaSz) != WOLFSSL_SUCCESS) {
15948
0
            WOLFSSL_MSG("Error setting the string");
15949
0
            wolfSSL_ASN1_STRING_free(ret);
15950
0
            ret = NULL;
15951
0
        }
15952
0
    }
15953
15954
0
    return ret;
15955
0
}
15956
#endif /* !WOLFSSL_USER_IO */
15957
15958
/* Is the specified cipher suite a fake one used an an extension proxy? */
15959
static WC_INLINE int SCSV_Check(byte suite0, byte suite)
15960
0
{
15961
0
    (void)suite0;
15962
0
    (void)suite;
15963
#ifdef HAVE_RENEGOTIATION_INDICATION
15964
    if (suite0 == CIPHER_BYTE && suite == TLS_EMPTY_RENEGOTIATION_INFO_SCSV)
15965
        return 1;
15966
#endif
15967
0
    return 0;
15968
0
}
15969
15970
static WC_INLINE int sslCipherMinMaxCheck(const WOLFSSL *ssl, byte suite0,
15971
        byte suite)
15972
0
{
15973
0
    const CipherSuiteInfo* cipher_names = GetCipherNames();
15974
0
    int cipherSz = GetCipherNamesSize();
15975
0
    int i;
15976
0
    for (i = 0; i < cipherSz; i++)
15977
0
        if (cipher_names[i].cipherSuite0 == suite0 &&
15978
0
                cipher_names[i].cipherSuite == suite)
15979
0
            break;
15980
0
    if (i == cipherSz)
15981
0
        return 1;
15982
    /* Check min version */
15983
0
    if (cipher_names[i].minor < ssl->options.minDowngrade) {
15984
0
        if (ssl->options.minDowngrade <= TLSv1_2_MINOR &&
15985
0
                cipher_names[i].minor >= TLSv1_MINOR)
15986
            /* 1.0 ciphersuites are in general available in 1.1 and
15987
             * 1.1 ciphersuites are in general available in 1.2 */
15988
0
            return 0;
15989
0
        return 1;
15990
0
    }
15991
    /* Check max version */
15992
0
    switch (cipher_names[i].minor) {
15993
0
    case SSLv3_MINOR :
15994
0
        return ssl->options.mask & WOLFSSL_OP_NO_SSLv3;
15995
0
    case TLSv1_MINOR :
15996
0
        return ssl->options.mask & WOLFSSL_OP_NO_TLSv1;
15997
0
    case TLSv1_1_MINOR :
15998
0
        return ssl->options.mask & WOLFSSL_OP_NO_TLSv1_1;
15999
0
    case TLSv1_2_MINOR :
16000
0
        return ssl->options.mask & WOLFSSL_OP_NO_TLSv1_2;
16001
0
    case TLSv1_3_MINOR :
16002
0
        return ssl->options.mask & WOLFSSL_OP_NO_TLSv1_3;
16003
0
    default:
16004
0
        WOLFSSL_MSG("Unrecognized minor version");
16005
0
        return 1;
16006
0
    }
16007
0
}
16008
16009
/* returns a pointer to internal cipher suite list. Should not be free'd by
16010
 * caller.
16011
 */
16012
WOLF_STACK_OF(WOLFSSL_CIPHER) *wolfSSL_get_ciphers_compat(const WOLFSSL *ssl)
16013
0
{
16014
0
    WOLF_STACK_OF(WOLFSSL_CIPHER)* ret = NULL;
16015
0
    const Suites* suites;
16016
0
#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
16017
0
    const CipherSuiteInfo* cipher_names = GetCipherNames();
16018
0
    int cipherSz = GetCipherNamesSize();
16019
0
#endif
16020
16021
0
    WOLFSSL_ENTER("wolfSSL_get_ciphers_compat");
16022
0
    if (ssl == NULL)
16023
0
        return NULL;
16024
16025
0
    suites = WOLFSSL_SUITES(ssl);
16026
0
    if (suites == NULL)
16027
0
        return NULL;
16028
16029
    /* check if stack needs populated */
16030
0
    if (ssl->suitesStack == NULL) {
16031
0
        int i;
16032
0
#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
16033
0
        int j;
16034
16035
        /* higher priority of cipher suite will be on top of stack */
16036
0
        for (i = suites->suiteSz - 2; i >=0; i-=2) {
16037
#else
16038
        for (i = 0; i < suites->suiteSz; i+=2) {
16039
#endif
16040
0
            WOLFSSL_STACK* add;
16041
16042
            /* A couple of suites are placeholders for special options,
16043
             * skip those. */
16044
0
            if (SCSV_Check(suites->suites[i], suites->suites[i+1])
16045
0
                    || sslCipherMinMaxCheck(ssl, suites->suites[i],
16046
0
                                            suites->suites[i+1])) {
16047
0
                continue;
16048
0
            }
16049
16050
0
            add = wolfSSL_sk_new_node(ssl->heap);
16051
0
            if (add != NULL) {
16052
0
                add->type = STACK_TYPE_CIPHER;
16053
0
                add->data.cipher.cipherSuite0 = suites->suites[i];
16054
0
                add->data.cipher.cipherSuite  = suites->suites[i+1];
16055
0
                add->data.cipher.ssl          = ssl;
16056
0
#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT)
16057
0
                for (j = 0; j < cipherSz; j++) {
16058
0
                    if (cipher_names[j].cipherSuite0 ==
16059
0
                            add->data.cipher.cipherSuite0 &&
16060
0
                            cipher_names[j].cipherSuite ==
16061
0
                                    add->data.cipher.cipherSuite) {
16062
0
                        add->data.cipher.offset = (unsigned long)j;
16063
0
                        break;
16064
0
                    }
16065
0
                }
16066
0
#endif
16067
0
                #if defined(WOLFSSL_QT) || defined(OPENSSL_ALL)
16068
                /* in_stack is checked in wolfSSL_CIPHER_description */
16069
0
                add->data.cipher.in_stack     = 1;
16070
0
                #endif
16071
16072
0
                add->next = ret;
16073
0
                if (ret != NULL) {
16074
0
                    add->num = ret->num + 1;
16075
0
                }
16076
0
                else {
16077
0
                    add->num = 1;
16078
0
                }
16079
0
                ret = add;
16080
0
            }
16081
0
        }
16082
0
        ((WOLFSSL*)ssl)->suitesStack = ret;
16083
0
    }
16084
0
    return ssl->suitesStack;
16085
0
}
16086
#endif /* OPENSSL_EXTRA || OPENSSL_ALL || WOLFSSL_NGINX || WOLFSSL_HAPROXY */
16087
#ifdef OPENSSL_ALL
16088
/* returned pointer is to an internal element in WOLFSSL struct and should not
16089
 * be free'd. It gets free'd when the WOLFSSL struct is free'd. */
16090
WOLF_STACK_OF(WOLFSSL_CIPHER)*  wolfSSL_get_client_ciphers(WOLFSSL* ssl)
16091
0
{
16092
0
    WOLF_STACK_OF(WOLFSSL_CIPHER)* ret = NULL;
16093
0
    const CipherSuiteInfo* cipher_names = GetCipherNames();
16094
0
    int cipherSz = GetCipherNamesSize();
16095
0
    const Suites* suites;
16096
16097
0
    WOLFSSL_ENTER("wolfSSL_get_client_ciphers");
16098
16099
0
    if (ssl == NULL) {
16100
0
        return NULL;
16101
0
    }
16102
16103
    /* return NULL if is client side */
16104
0
    if (wolfSSL_is_server(ssl) == 0) {
16105
0
        return NULL;
16106
0
    }
16107
16108
0
    suites = ssl->clSuites;
16109
0
    if (suites == NULL) {
16110
0
        WOLFSSL_MSG("No client suites stored");
16111
0
    }
16112
0
    else if (ssl->clSuitesStack != NULL) {
16113
0
        ret = ssl->clSuitesStack;
16114
0
    }
16115
0
    else { /* generate cipher suites stack if not already done */
16116
0
        int i;
16117
0
        int j;
16118
16119
0
        ret = wolfSSL_sk_new_node(ssl->heap);
16120
0
        if (ret != NULL) {
16121
0
            ret->type = STACK_TYPE_CIPHER;
16122
16123
            /* higher priority of cipher suite will be on top of stack */
16124
0
            for (i = suites->suiteSz - 2; i >= 0; i -= 2) {
16125
0
                WOLFSSL_CIPHER cipher;
16126
16127
                /* A couple of suites are placeholders for special options,
16128
                 * skip those. */
16129
0
                if (SCSV_Check(suites->suites[i], suites->suites[i+1])
16130
0
                        || sslCipherMinMaxCheck(ssl, suites->suites[i],
16131
0
                                                suites->suites[i+1])) {
16132
0
                    continue;
16133
0
                }
16134
16135
0
                cipher.cipherSuite0 = suites->suites[i];
16136
0
                cipher.cipherSuite  = suites->suites[i+1];
16137
0
                cipher.ssl          = ssl;
16138
0
                for (j = 0; j < cipherSz; j++) {
16139
0
                    if (cipher_names[j].cipherSuite0 ==
16140
0
                            cipher.cipherSuite0 &&
16141
0
                            cipher_names[j].cipherSuite ==
16142
0
                                    cipher.cipherSuite) {
16143
0
                        cipher.offset = (unsigned long)j;
16144
0
                        break;
16145
0
                    }
16146
0
                }
16147
16148
                /* in_stack is checked in wolfSSL_CIPHER_description */
16149
0
                cipher.in_stack     = 1;
16150
16151
0
                if (wolfSSL_sk_CIPHER_push(ret, &cipher) <= 0) {
16152
0
                    WOLFSSL_MSG("Error pushing client cipher onto stack");
16153
0
                    wolfSSL_sk_CIPHER_free(ret);
16154
0
                    ret = NULL;
16155
0
                    break;
16156
0
                }
16157
0
            }
16158
0
        }
16159
0
        ssl->clSuitesStack = ret;
16160
0
    }
16161
0
    return ret;
16162
0
}
16163
#endif /* OPENSSL_ALL */
16164
16165
#if defined(OPENSSL_EXTRA) || defined(HAVE_SECRET_CALLBACK)
16166
long wolfSSL_SSL_CTX_get_timeout(const WOLFSSL_CTX *ctx)
16167
0
{
16168
0
    WOLFSSL_ENTER("wolfSSL_SSL_CTX_get_timeout");
16169
16170
0
    if (ctx == NULL)
16171
0
        return 0;
16172
16173
0
    return ctx->timeout;
16174
0
}
16175
16176
16177
/* returns the time in seconds of the current timeout */
16178
long wolfSSL_get_timeout(WOLFSSL* ssl)
16179
0
{
16180
0
    WOLFSSL_ENTER("wolfSSL_get_timeout");
16181
16182
0
    if (ssl == NULL)
16183
0
        return 0;
16184
0
    return ssl->timeout;
16185
0
}
16186
#endif
16187
16188
#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) \
16189
    || defined(OPENSSL_EXTRA) || defined(HAVE_LIGHTY)
16190
16191
#ifdef HAVE_ECC
16192
int wolfSSL_SSL_CTX_set_tmp_ecdh(WOLFSSL_CTX *ctx, WOLFSSL_EC_KEY *ecdh)
16193
0
{
16194
0
    WOLFSSL_ENTER("wolfSSL_SSL_CTX_set_tmp_ecdh");
16195
16196
0
    if (ctx == NULL || ecdh == NULL)
16197
0
        return BAD_FUNC_ARG;
16198
16199
0
    ctx->ecdhCurveOID = (word32)ecdh->group->curve_oid;
16200
16201
0
    return WOLFSSL_SUCCESS;
16202
0
}
16203
#endif
16204
#ifndef NO_BIO
16205
WOLFSSL_BIO *wolfSSL_SSL_get_rbio(const WOLFSSL *s)
16206
0
{
16207
0
    WOLFSSL_ENTER("wolfSSL_SSL_get_rbio");
16208
    /* Nginx sets the buffer size if the read BIO is different to write BIO.
16209
     * The setting buffer size doesn't do anything so return NULL for both.
16210
     */
16211
0
    if (s == NULL)
16212
0
        return NULL;
16213
16214
0
    return s->biord;
16215
0
}
16216
WOLFSSL_BIO *wolfSSL_SSL_get_wbio(const WOLFSSL *s)
16217
0
{
16218
0
    WOLFSSL_ENTER("wolfSSL_SSL_get_wbio");
16219
0
    (void)s;
16220
    /* Nginx sets the buffer size if the read BIO is different to write BIO.
16221
     * The setting buffer size doesn't do anything so return NULL for both.
16222
     */
16223
0
    if (s == NULL)
16224
0
        return NULL;
16225
16226
0
    return s->biowr;
16227
0
}
16228
#endif /* !NO_BIO */
16229
16230
#ifndef NO_TLS
16231
int wolfSSL_SSL_do_handshake_internal(WOLFSSL *s)
16232
0
{
16233
0
    WOLFSSL_ENTER("wolfSSL_SSL_do_handshake_internal");
16234
0
    if (s == NULL)
16235
0
        return WOLFSSL_FAILURE;
16236
16237
0
    if (s->options.side == WOLFSSL_CLIENT_END) {
16238
0
    #ifndef NO_WOLFSSL_CLIENT
16239
0
        return wolfSSL_connect(s);
16240
    #else
16241
        WOLFSSL_MSG("Client not compiled in");
16242
        return WOLFSSL_FAILURE;
16243
    #endif
16244
0
    }
16245
16246
0
#ifndef NO_WOLFSSL_SERVER
16247
0
    return wolfSSL_accept(s);
16248
#else
16249
    WOLFSSL_MSG("Server not compiled in");
16250
    return WOLFSSL_FAILURE;
16251
#endif
16252
0
}
16253
16254
int wolfSSL_SSL_do_handshake(WOLFSSL *s)
16255
0
{
16256
0
    WOLFSSL_ENTER("wolfSSL_SSL_do_handshake");
16257
#ifdef WOLFSSL_QUIC
16258
    if (WOLFSSL_IS_QUIC(s)) {
16259
        return wolfSSL_quic_do_handshake(s);
16260
    }
16261
#endif
16262
0
    return wolfSSL_SSL_do_handshake_internal(s);
16263
0
}
16264
#endif /* !NO_TLS */
16265
16266
#if defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x10100000L
16267
int wolfSSL_SSL_in_init(const WOLFSSL *ssl)
16268
#else
16269
int wolfSSL_SSL_in_init(WOLFSSL *ssl)
16270
#endif
16271
0
{
16272
0
    WOLFSSL_ENTER("wolfSSL_SSL_in_init");
16273
16274
0
    return !wolfSSL_is_init_finished(ssl);
16275
0
}
16276
16277
int wolfSSL_SSL_in_before(const WOLFSSL *ssl)
16278
0
{
16279
0
    WOLFSSL_ENTER("wolfSSL_SSL_in_before");
16280
16281
0
    if (ssl == NULL)
16282
0
        return WOLFSSL_FAILURE;
16283
16284
0
    return ssl->options.handShakeState == NULL_STATE;
16285
0
}
16286
16287
int wolfSSL_SSL_in_connect_init(WOLFSSL* ssl)
16288
0
{
16289
0
    WOLFSSL_ENTER("wolfSSL_SSL_in_connect_init");
16290
16291
0
    if (ssl == NULL)
16292
0
        return WOLFSSL_FAILURE;
16293
16294
0
    if (ssl->options.side == WOLFSSL_CLIENT_END) {
16295
0
        return ssl->options.connectState > CONNECT_BEGIN &&
16296
0
            ssl->options.connectState < SECOND_REPLY_DONE;
16297
0
    }
16298
16299
0
    return ssl->options.acceptState > ACCEPT_BEGIN &&
16300
0
        ssl->options.acceptState < ACCEPT_THIRD_REPLY_DONE;
16301
0
}
16302
16303
#if defined(HAVE_SESSION_TICKET) && !defined(NO_WOLFSSL_SERVER)
16304
/* Expected return values from implementations of OpenSSL ticket key callback.
16305
 */
16306
#define TICKET_KEY_CB_RET_FAILURE    (-1)
16307
#define TICKET_KEY_CB_RET_NOT_FOUND   0
16308
0
#define TICKET_KEY_CB_RET_OK          1
16309
0
#define TICKET_KEY_CB_RET_RENEW       2
16310
16311
/* Implementation of session ticket encryption/decryption using OpenSSL
16312
 * callback to initialize the cipher and HMAC.
16313
 *
16314
 * ssl           The SSL/TLS object.
16315
 * keyName       The key name - used to identify the key to be used.
16316
 * iv            The IV to use.
16317
 * mac           The MAC of the encrypted data.
16318
 * enc           Encrypt ticket.
16319
 * encTicket     The ticket data.
16320
 * encTicketLen  The length of the ticket data.
16321
 * encLen        The encrypted/decrypted ticket length - output length.
16322
 * ctx           Ignored. Application specific data.
16323
 * returns WOLFSSL_TICKET_RET_OK to indicate success,
16324
 *         WOLFSSL_TICKET_RET_CREATE if a new ticket is required and
16325
 *         WOLFSSL_TICKET_RET_FATAL on error.
16326
 */
16327
static int wolfSSL_TicketKeyCb(WOLFSSL* ssl,
16328
        unsigned char keyName[WOLFSSL_TICKET_NAME_SZ],
16329
        unsigned char iv[WOLFSSL_TICKET_IV_SZ],
16330
        unsigned char mac[WOLFSSL_TICKET_MAC_SZ],
16331
        int enc, unsigned char* encTicket,
16332
        int encTicketLen, int* encLen, void* ctx)
16333
0
{
16334
0
    byte                    digest[WC_MAX_DIGEST_SIZE];
16335
0
    WC_DECLARE_VAR(evpCtx, WOLFSSL_EVP_CIPHER_CTX, 1, 0);
16336
0
    WOLFSSL_HMAC_CTX        hmacCtx;
16337
0
    unsigned int            mdSz = 0;
16338
0
    int                     len = 0;
16339
0
    int                     ret = WOLFSSL_TICKET_RET_FATAL;
16340
0
    int                     res;
16341
0
    int                     totalSz = 0;
16342
16343
0
    (void)ctx;
16344
16345
0
    WOLFSSL_ENTER("wolfSSL_TicketKeyCb");
16346
16347
0
    if (ssl == NULL || ssl->ctx == NULL || ssl->ctx->ticketEncWrapCb == NULL) {
16348
0
        WOLFSSL_MSG("Bad parameter");
16349
0
        return WOLFSSL_TICKET_RET_FATAL;
16350
0
    }
16351
16352
0
#ifdef WOLFSSL_SMALL_STACK
16353
0
    evpCtx = (WOLFSSL_EVP_CIPHER_CTX *)XMALLOC(sizeof(*evpCtx), ssl->heap,
16354
0
                                               DYNAMIC_TYPE_TMP_BUFFER);
16355
0
    if (evpCtx == NULL) {
16356
0
        WOLFSSL_MSG("out of memory");
16357
0
        return WOLFSSL_TICKET_RET_FATAL;
16358
0
    }
16359
0
#endif
16360
16361
    /* Initialize the cipher and HMAC. */
16362
0
    wolfSSL_EVP_CIPHER_CTX_init(evpCtx);
16363
0
    if (wolfSSL_HMAC_CTX_Init(&hmacCtx) != WOLFSSL_SUCCESS) {
16364
0
        WOLFSSL_MSG("wolfSSL_HMAC_CTX_Init error");
16365
0
        WC_FREE_VAR_EX(evpCtx, ssl->heap, DYNAMIC_TYPE_TMP_BUFFER);
16366
0
        return WOLFSSL_TICKET_RET_FATAL;
16367
0
    }
16368
0
    res = ssl->ctx->ticketEncWrapCb(ssl, keyName,
16369
0
            iv, evpCtx, &hmacCtx, enc);
16370
0
    if (res != TICKET_KEY_CB_RET_OK && res != TICKET_KEY_CB_RET_RENEW) {
16371
0
        WOLFSSL_MSG("Ticket callback error");
16372
0
        ret = WOLFSSL_TICKET_RET_FATAL;
16373
0
        goto end;
16374
0
    }
16375
16376
0
    if (wolfSSL_HMAC_size(&hmacCtx) > WOLFSSL_TICKET_MAC_SZ) {
16377
0
        WOLFSSL_MSG("Ticket cipher MAC size error");
16378
0
        goto end;
16379
0
    }
16380
16381
0
    if (enc)
16382
0
    {
16383
        /* Encrypt in place. */
16384
0
        if (!wolfSSL_EVP_CipherUpdate(evpCtx, encTicket, &len,
16385
0
                                      encTicket, encTicketLen))
16386
0
            goto end;
16387
0
        totalSz = len;
16388
0
        if (totalSz > *encLen)
16389
0
            goto end;
16390
0
        if (!wolfSSL_EVP_EncryptFinal(evpCtx, &encTicket[len], &len))
16391
0
            goto end;
16392
        /* Total length of encrypted data. */
16393
0
        totalSz += len;
16394
0
        if (totalSz > *encLen)
16395
0
            goto end;
16396
16397
        /* HMAC the encrypted data into the parameter 'mac'. */
16398
0
        if (!wolfSSL_HMAC_Update(&hmacCtx, encTicket, totalSz))
16399
0
            goto end;
16400
0
        if (!wolfSSL_HMAC_Final(&hmacCtx, mac, &mdSz))
16401
0
            goto end;
16402
0
    }
16403
0
    else
16404
0
    {
16405
        /* HMAC the encrypted data and compare it to the passed in data. */
16406
0
        if (!wolfSSL_HMAC_Update(&hmacCtx, encTicket, encTicketLen))
16407
0
            goto end;
16408
0
        if (!wolfSSL_HMAC_Final(&hmacCtx, digest, &mdSz))
16409
0
            goto end;
16410
0
        if (XMEMCMP(mac, digest, mdSz) != 0)
16411
0
            goto end;
16412
16413
        /* Decrypt the ticket data in place. */
16414
0
        if (!wolfSSL_EVP_CipherUpdate(evpCtx, encTicket, &len,
16415
0
                                      encTicket, encTicketLen))
16416
0
            goto end;
16417
0
        totalSz = len;
16418
0
        if (totalSz > encTicketLen)
16419
0
            goto end;
16420
0
        if (!wolfSSL_EVP_DecryptFinal(evpCtx, &encTicket[len], &len))
16421
0
            goto end;
16422
        /* Total length of decrypted data. */
16423
0
        totalSz += len;
16424
0
        if (totalSz > encTicketLen)
16425
0
            goto end;
16426
0
    }
16427
0
    *encLen = totalSz;
16428
16429
0
    if (res == TICKET_KEY_CB_RET_RENEW && !IsAtLeastTLSv1_3(ssl->version)
16430
0
            && !enc)
16431
0
        ret = WOLFSSL_TICKET_RET_CREATE;
16432
0
    else
16433
0
        ret = WOLFSSL_TICKET_RET_OK;
16434
0
end:
16435
16436
0
    (void)wc_HmacFree(&hmacCtx.hmac);
16437
0
    (void)wolfSSL_EVP_CIPHER_CTX_cleanup(evpCtx);
16438
16439
0
    WC_FREE_VAR_EX(evpCtx, ssl->heap, DYNAMIC_TYPE_TMP_BUFFER);
16440
16441
0
    return ret;
16442
0
}
16443
16444
/* Set the callback to use when encrypting/decrypting tickets.
16445
 *
16446
 * ctx  The SSL/TLS context object.
16447
 * cb   The OpenSSL session ticket callback.
16448
 * returns WOLFSSL_SUCCESS to indicate success.
16449
 */
16450
int wolfSSL_CTX_set_tlsext_ticket_key_cb(WOLFSSL_CTX *ctx, ticketCompatCb cb)
16451
0
{
16452
16453
    /* Set the ticket encryption callback to be a wrapper around OpenSSL
16454
     * callback.
16455
     */
16456
0
    ctx->ticketEncCb = wolfSSL_TicketKeyCb;
16457
0
    ctx->ticketEncWrapCb = cb;
16458
16459
0
    return WOLFSSL_SUCCESS;
16460
0
}
16461
16462
#endif /* HAVE_SESSION_TICKET */
16463
16464
#endif /* OPENSSL_ALL || WOLFSSL_NGINX || WOLFSSL_HAPROXY ||
16465
    OPENSSL_EXTRA || HAVE_LIGHTY */
16466
16467
#if defined(HAVE_SESSION_TICKET) && !defined(WOLFSSL_NO_DEF_TICKET_ENC_CB) && \
16468
    !defined(NO_WOLFSSL_SERVER)
16469
/* Serialize the session ticket encryption keys.
16470
 *
16471
 * @param [in]  ctx     SSL/TLS context object.
16472
 * @param [in]  keys    Buffer to hold session ticket keys.
16473
 * @param [in]  keylen  Length of buffer.
16474
 * @return  WOLFSSL_SUCCESS on success.
16475
 * @return  WOLFSSL_FAILURE when ctx is NULL, keys is NULL or keylen is not the
16476
 *          correct length.
16477
 */
16478
long wolfSSL_CTX_get_tlsext_ticket_keys(WOLFSSL_CTX *ctx,
16479
     unsigned char *keys, int keylen)
16480
0
{
16481
0
    if (ctx == NULL || keys == NULL) {
16482
0
        return WOLFSSL_FAILURE;
16483
0
    }
16484
0
    if (keylen != WOLFSSL_TICKET_KEYS_SZ) {
16485
0
        return WOLFSSL_FAILURE;
16486
0
    }
16487
16488
0
    XMEMCPY(keys, ctx->ticketKeyCtx.name, WOLFSSL_TICKET_NAME_SZ);
16489
0
    keys += WOLFSSL_TICKET_NAME_SZ;
16490
0
    XMEMCPY(keys, ctx->ticketKeyCtx.key[0], WOLFSSL_TICKET_KEY_SZ);
16491
0
    keys += WOLFSSL_TICKET_KEY_SZ;
16492
0
    XMEMCPY(keys, ctx->ticketKeyCtx.key[1], WOLFSSL_TICKET_KEY_SZ);
16493
0
    keys += WOLFSSL_TICKET_KEY_SZ;
16494
0
    c32toa(ctx->ticketKeyCtx.expirary[0], keys);
16495
0
    keys += OPAQUE32_LEN;
16496
0
    c32toa(ctx->ticketKeyCtx.expirary[1], keys);
16497
16498
0
    return WOLFSSL_SUCCESS;
16499
0
}
16500
16501
/* Deserialize the session ticket encryption keys.
16502
 *
16503
 * @param [in]  ctx     SSL/TLS context object.
16504
 * @param [in]  keys    Session ticket keys.
16505
 * @param [in]  keylen  Length of data.
16506
 * @return  WOLFSSL_SUCCESS on success.
16507
 * @return  WOLFSSL_FAILURE when ctx is NULL, keys is NULL or keylen is not the
16508
 *          correct length.
16509
 */
16510
long wolfSSL_CTX_set_tlsext_ticket_keys(WOLFSSL_CTX *ctx,
16511
     const void *keys_vp, int keylen)
16512
0
{
16513
0
    const byte* keys = (const byte*)keys_vp;
16514
0
    if (ctx == NULL || keys == NULL) {
16515
0
        return WOLFSSL_FAILURE;
16516
0
    }
16517
0
    if (keylen != WOLFSSL_TICKET_KEYS_SZ) {
16518
0
        return WOLFSSL_FAILURE;
16519
0
    }
16520
16521
0
    XMEMCPY(ctx->ticketKeyCtx.name, keys, WOLFSSL_TICKET_NAME_SZ);
16522
0
    keys += WOLFSSL_TICKET_NAME_SZ;
16523
0
    XMEMCPY(ctx->ticketKeyCtx.key[0], keys, WOLFSSL_TICKET_KEY_SZ);
16524
0
    keys += WOLFSSL_TICKET_KEY_SZ;
16525
0
    XMEMCPY(ctx->ticketKeyCtx.key[1], keys, WOLFSSL_TICKET_KEY_SZ);
16526
0
    keys += WOLFSSL_TICKET_KEY_SZ;
16527
0
    ato32(keys, &ctx->ticketKeyCtx.expirary[0]);
16528
0
    keys += OPAQUE32_LEN;
16529
0
    ato32(keys, &ctx->ticketKeyCtx.expirary[1]);
16530
16531
0
    return WOLFSSL_SUCCESS;
16532
0
}
16533
#endif
16534
16535
#if defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) || \
16536
    defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL)
16537
int wolfSSL_CTX_get_extra_chain_certs(WOLFSSL_CTX* ctx,
16538
    WOLF_STACK_OF(X509)** chain)
16539
0
{
16540
0
    word32         idx;
16541
0
    word32         length;
16542
0
    WOLFSSL_STACK* node;
16543
0
    WOLFSSL_STACK* last = NULL;
16544
16545
0
    if (ctx == NULL || chain == NULL) {
16546
0
        chain = NULL;
16547
0
        return WOLFSSL_FAILURE;
16548
0
    }
16549
0
    if (ctx->x509Chain != NULL) {
16550
0
        *chain = ctx->x509Chain;
16551
0
        return WOLFSSL_SUCCESS;
16552
0
    }
16553
16554
    /* If there are no chains then success! */
16555
0
    *chain = NULL;
16556
0
    if (ctx->certChain == NULL || ctx->certChain->length == 0) {
16557
0
        return WOLFSSL_SUCCESS;
16558
0
    }
16559
16560
    /* Create a new stack of WOLFSSL_X509 object from chain buffer. */
16561
0
    for (idx = 0; idx < ctx->certChain->length; ) {
16562
0
        node = wolfSSL_sk_X509_new_null();
16563
0
        if (node == NULL)
16564
0
            return WOLFSSL_FAILURE;
16565
0
        node->next = NULL;
16566
16567
        /* 3 byte length | X509 DER data */
16568
0
        ato24(ctx->certChain->buffer + idx, &length);
16569
0
        idx += 3;
16570
16571
        /* Create a new X509 from DER encoded data. */
16572
0
        node->data.x509 = wolfSSL_X509_d2i_ex(NULL,
16573
0
            ctx->certChain->buffer + idx, (int)length, ctx->heap);
16574
0
        if (node->data.x509 == NULL) {
16575
0
            XFREE(node, NULL, DYNAMIC_TYPE_OPENSSL);
16576
            /* Return as much of the chain as we created. */
16577
0
            ctx->x509Chain = *chain;
16578
0
            return WOLFSSL_FAILURE;
16579
0
        }
16580
0
        idx += length;
16581
16582
        /* Add object to the end of the stack. */
16583
0
        if (last == NULL) {
16584
0
            node->num = 1;
16585
0
            *chain = node;
16586
0
        }
16587
0
        else {
16588
0
            (*chain)->num++;
16589
0
            last->next = node;
16590
0
        }
16591
16592
0
        last = node;
16593
0
    }
16594
16595
0
    ctx->x509Chain = *chain;
16596
16597
0
    return WOLFSSL_SUCCESS;
16598
0
}
16599
16600
int wolfSSL_CTX_get0_chain_certs(WOLFSSL_CTX *ctx,
16601
        WOLF_STACK_OF(WOLFSSL_X509) **sk)
16602
0
{
16603
0
    WOLFSSL_ENTER("wolfSSL_CTX_get0_chain_certs");
16604
0
    if (ctx == NULL || sk == NULL) {
16605
0
        WOLFSSL_MSG("Bad parameter");
16606
0
        return WOLFSSL_FAILURE;
16607
0
    }
16608
16609
    /* This function should return ctx->x509Chain if it is populated, otherwise
16610
       it should be populated from ctx->certChain.  This matches the behavior of
16611
       wolfSSL_CTX_get_extra_chain_certs, so it is used directly. */
16612
0
    return wolfSSL_CTX_get_extra_chain_certs(ctx, sk);
16613
0
}
16614
16615
#ifdef KEEP_OUR_CERT
16616
int wolfSSL_get0_chain_certs(WOLFSSL *ssl,
16617
        WOLF_STACK_OF(WOLFSSL_X509) **sk)
16618
0
{
16619
0
    WOLFSSL_ENTER("wolfSSL_get0_chain_certs");
16620
0
    if (ssl == NULL || sk == NULL) {
16621
0
        WOLFSSL_MSG("Bad parameter");
16622
0
        return WOLFSSL_FAILURE;
16623
0
    }
16624
0
    *sk = ssl->ourCertChain;
16625
0
    return WOLFSSL_SUCCESS;
16626
0
}
16627
#endif
16628
16629
void wolfSSL_WOLFSSL_STRING_free(WOLFSSL_STRING s)
16630
0
{
16631
0
    WOLFSSL_ENTER("wolfSSL_WOLFSSL_STRING_free");
16632
16633
0
    XFREE(s, NULL, DYNAMIC_TYPE_OPENSSL);
16634
0
}
16635
16636
#endif /* WOLFSSL_NGINX || WOLFSSL_HAPROXY || OPENSSL_EXTRA || OPENSSL_ALL */
16637
16638
#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || \
16639
    defined(WOLFSSL_HAPROXY) || defined(HAVE_LIGHTY) || \
16640
    defined(WOLFSSL_QUIC)
16641
#ifdef HAVE_ALPN
16642
void wolfSSL_get0_alpn_selected(const WOLFSSL *ssl, const unsigned char **data,
16643
                                unsigned int *len)
16644
{
16645
    word16 nameLen = 0;
16646
16647
    if (ssl != NULL && data != NULL && len != NULL) {
16648
        TLSX_ALPN_GetRequest(ssl->extensions, (void **)data, &nameLen);
16649
        *len = nameLen;
16650
    }
16651
}
16652
16653
int wolfSSL_select_next_proto(unsigned char **out, unsigned char *outLen,
16654
                              const unsigned char *in, unsigned int inLen,
16655
                              const unsigned char *clientNames,
16656
                              unsigned int clientLen)
16657
{
16658
    unsigned int i, j;
16659
    byte lenIn, lenClient;
16660
16661
    if (out == NULL || outLen == NULL || in == NULL || clientNames == NULL)
16662
        return WOLFSSL_NPN_UNSUPPORTED;
16663
16664
    for (i = 0; i < inLen; i += lenIn) {
16665
        lenIn = in[i++];
16666
        for (j = 0; j < clientLen; j += lenClient) {
16667
            lenClient = clientNames[j++];
16668
16669
            if (lenIn != lenClient)
16670
                continue;
16671
16672
            if (XMEMCMP(in + i, clientNames + j, lenIn) == 0) {
16673
                *out = (unsigned char *)(in + i);
16674
                *outLen = lenIn;
16675
                return WOLFSSL_NPN_NEGOTIATED;
16676
            }
16677
        }
16678
    }
16679
16680
    *out = (unsigned char *)clientNames + 1;
16681
    *outLen = clientNames[0];
16682
    return WOLFSSL_NPN_NO_OVERLAP;
16683
}
16684
16685
void wolfSSL_set_alpn_select_cb(WOLFSSL *ssl,
16686
                                int (*cb) (WOLFSSL *ssl,
16687
                                           const unsigned char **out,
16688
                                           unsigned char *outlen,
16689
                                           const unsigned char *in,
16690
                                           unsigned int inlen,
16691
                                           void *arg), void *arg)
16692
{
16693
    if (ssl != NULL) {
16694
        ssl->alpnSelect = cb;
16695
        ssl->alpnSelectArg = arg;
16696
    }
16697
}
16698
16699
void wolfSSL_CTX_set_alpn_select_cb(WOLFSSL_CTX *ctx,
16700
                                    int (*cb) (WOLFSSL *ssl,
16701
                                               const unsigned char **out,
16702
                                               unsigned char *outlen,
16703
                                               const unsigned char *in,
16704
                                               unsigned int inlen,
16705
                                               void *arg), void *arg)
16706
{
16707
    if (ctx != NULL) {
16708
        ctx->alpnSelect = cb;
16709
        ctx->alpnSelectArg = arg;
16710
    }
16711
}
16712
16713
void wolfSSL_CTX_set_next_protos_advertised_cb(WOLFSSL_CTX *s,
16714
                                           int (*cb) (WOLFSSL *ssl,
16715
                                                      const unsigned char
16716
                                                      **out,
16717
                                                      unsigned int *outlen,
16718
                                                      void *arg), void *arg)
16719
{
16720
    (void)s;
16721
    (void)cb;
16722
    (void)arg;
16723
    WOLFSSL_STUB("wolfSSL_CTX_set_next_protos_advertised_cb");
16724
}
16725
16726
void wolfSSL_CTX_set_next_proto_select_cb(WOLFSSL_CTX *s,
16727
                                      int (*cb) (WOLFSSL *ssl,
16728
                                                 unsigned char **out,
16729
                                                 unsigned char *outlen,
16730
                                                 const unsigned char *in,
16731
                                                 unsigned int inlen,
16732
                                                 void *arg), void *arg)
16733
{
16734
    (void)s;
16735
    (void)cb;
16736
    (void)arg;
16737
    WOLFSSL_STUB("wolfSSL_CTX_set_next_proto_select_cb");
16738
}
16739
16740
void wolfSSL_get0_next_proto_negotiated(const WOLFSSL *s,
16741
    const unsigned char **data, unsigned *len)
16742
{
16743
    (void)s;
16744
    (void)data;
16745
    (void)len;
16746
    WOLFSSL_STUB("wolfSSL_get0_next_proto_negotiated");
16747
}
16748
#endif /* HAVE_ALPN */
16749
16750
#endif /* WOLFSSL_NGINX  / WOLFSSL_HAPROXY */
16751
16752
#if defined(OPENSSL_EXTRA) || defined(HAVE_CURL)
16753
int wolfSSL_curve_is_disabled(const WOLFSSL* ssl, word16 curve_id)
16754
9.24k
{
16755
9.24k
    int ret = 0;
16756
16757
9.24k
    WOLFSSL_ENTER("wolfSSL_curve_is_disabled");
16758
9.24k
    WOLFSSL_MSG_EX("wolfSSL_curve_is_disabled checking for %d", curve_id);
16759
16760
    /* (curve_id >= WOLFSSL_FFDHE_START) - DH parameters are never disabled. */
16761
9.24k
    if (curve_id < WOLFSSL_FFDHE_START) {
16762
8.20k
        if (curve_id > WOLFSSL_ECC_MAX_AVAIL) {
16763
0
            WOLFSSL_MSG("Curve id out of supported range");
16764
            /* Disabled if not in valid range. */
16765
0
            ret = 1;
16766
0
        }
16767
8.20k
        else if (curve_id >= 32) {
16768
            /* 0 is for invalid and 1-14 aren't used otherwise. */
16769
119
            ret = (ssl->disabledCurves & (1U << (curve_id - 32))) != 0;
16770
119
        }
16771
8.08k
        else {
16772
8.08k
            ret = (ssl->disabledCurves & (1U << curve_id)) != 0;
16773
8.08k
        }
16774
8.20k
    }
16775
16776
9.24k
    WOLFSSL_LEAVE("wolfSSL_curve_is_disabled", ret);
16777
9.24k
    return ret;
16778
9.24k
}
16779
16780
#if (defined(HAVE_ECC) || \
16781
    defined(HAVE_CURVE25519) || defined(HAVE_CURVE448))
16782
#define CURVE_NAME(c) XSTR_SIZEOF((c)), (c)
16783
16784
const WOLF_EC_NIST_NAME kNistCurves[] = {
16785
#ifdef HAVE_ECC
16786
    {CURVE_NAME("P-160"),   WC_NID_secp160r1, WOLFSSL_ECC_SECP160R1},
16787
    {CURVE_NAME("P-160-2"), WC_NID_secp160r2, WOLFSSL_ECC_SECP160R2},
16788
    {CURVE_NAME("P-192"),   WC_NID_X9_62_prime192v1, WOLFSSL_ECC_SECP192R1},
16789
    {CURVE_NAME("P-224"),   WC_NID_secp224r1, WOLFSSL_ECC_SECP224R1},
16790
    {CURVE_NAME("P-256"),   WC_NID_X9_62_prime256v1, WOLFSSL_ECC_SECP256R1},
16791
    {CURVE_NAME("P-384"),   WC_NID_secp384r1, WOLFSSL_ECC_SECP384R1},
16792
    {CURVE_NAME("P-521"),   WC_NID_secp521r1, WOLFSSL_ECC_SECP521R1},
16793
    {CURVE_NAME("K-160"),   WC_NID_secp160k1, WOLFSSL_ECC_SECP160K1},
16794
    {CURVE_NAME("K-192"),   WC_NID_secp192k1, WOLFSSL_ECC_SECP192K1},
16795
    {CURVE_NAME("K-224"),   WC_NID_secp224k1, WOLFSSL_ECC_SECP224R1},
16796
    {CURVE_NAME("K-256"),   WC_NID_secp256k1, WOLFSSL_ECC_SECP256K1},
16797
    {CURVE_NAME("B-256"),   WC_NID_brainpoolP256r1,
16798
     WOLFSSL_ECC_BRAINPOOLP256R1},
16799
    {CURVE_NAME("B-384"),   WC_NID_brainpoolP384r1,
16800
     WOLFSSL_ECC_BRAINPOOLP384R1},
16801
    {CURVE_NAME("B-512"),   WC_NID_brainpoolP512r1,
16802
     WOLFSSL_ECC_BRAINPOOLP512R1},
16803
#endif
16804
#ifdef HAVE_CURVE25519
16805
    {CURVE_NAME("X25519"),  WC_NID_X25519, WOLFSSL_ECC_X25519},
16806
#endif
16807
#ifdef HAVE_CURVE448
16808
    {CURVE_NAME("X448"),    WC_NID_X448, WOLFSSL_ECC_X448},
16809
#endif
16810
#ifdef WOLFSSL_HAVE_MLKEM
16811
#ifndef WOLFSSL_NO_ML_KEM
16812
    {CURVE_NAME("ML_KEM_512"), WOLFSSL_ML_KEM_512, WOLFSSL_ML_KEM_512},
16813
    {CURVE_NAME("ML_KEM_768"), WOLFSSL_ML_KEM_768, WOLFSSL_ML_KEM_768},
16814
    {CURVE_NAME("ML_KEM_1024"), WOLFSSL_ML_KEM_1024, WOLFSSL_ML_KEM_1024},
16815
#if (defined(WOLFSSL_WC_MLKEM) || defined(HAVE_LIBOQS)) && defined(HAVE_ECC)
16816
    {CURVE_NAME("SecP256r1MLKEM512"), WOLFSSL_SECP256R1MLKEM512,
16817
     WOLFSSL_SECP256R1MLKEM512},
16818
    {CURVE_NAME("SecP384r1MLKEM768"), WOLFSSL_SECP384R1MLKEM768,
16819
     WOLFSSL_SECP384R1MLKEM768},
16820
    {CURVE_NAME("SecP256r1MLKEM768"), WOLFSSL_SECP256R1MLKEM768,
16821
     WOLFSSL_SECP256R1MLKEM768},
16822
    {CURVE_NAME("SecP521r1MLKEM1024"), WOLFSSL_SECP521R1MLKEM1024,
16823
     WOLFSSL_SECP521R1MLKEM1024},
16824
    {CURVE_NAME("SecP384r1MLKEM1024"), WOLFSSL_SECP384R1MLKEM1024,
16825
     WOLFSSL_SECP384R1MLKEM1024},
16826
    {CURVE_NAME("X25519MLKEM512"), WOLFSSL_X25519MLKEM512,
16827
     WOLFSSL_X25519MLKEM512},
16828
    {CURVE_NAME("X448MLKEM768"), WOLFSSL_X448MLKEM768,
16829
     WOLFSSL_X448MLKEM768},
16830
    {CURVE_NAME("X25519MLKEM768"), WOLFSSL_X25519MLKEM768,
16831
     WOLFSSL_X25519MLKEM768},
16832
#endif
16833
#endif /* !WOLFSSL_NO_ML_KEM */
16834
#ifdef WOLFSSL_MLKEM_KYBER
16835
    {CURVE_NAME("KYBER_LEVEL1"), WOLFSSL_KYBER_LEVEL1, WOLFSSL_KYBER_LEVEL1},
16836
    {CURVE_NAME("KYBER_LEVEL3"), WOLFSSL_KYBER_LEVEL3, WOLFSSL_KYBER_LEVEL3},
16837
    {CURVE_NAME("KYBER_LEVEL5"), WOLFSSL_KYBER_LEVEL5, WOLFSSL_KYBER_LEVEL5},
16838
#if (defined(WOLFSSL_WC_MLKEM) || defined(HAVE_LIBOQS)) && defined(HAVE_ECC)
16839
    {CURVE_NAME("P256_KYBER_LEVEL1"), WOLFSSL_P256_KYBER_LEVEL1,
16840
     WOLFSSL_P256_KYBER_LEVEL1},
16841
    {CURVE_NAME("P384_KYBER_LEVEL3"), WOLFSSL_P384_KYBER_LEVEL3,
16842
     WOLFSSL_P384_KYBER_LEVEL3},
16843
    {CURVE_NAME("P256_KYBER_LEVEL3"), WOLFSSL_P256_KYBER_LEVEL3,
16844
     WOLFSSL_P256_KYBER_LEVEL3},
16845
    {CURVE_NAME("P521_KYBER_LEVEL5"), WOLFSSL_P521_KYBER_LEVEL5,
16846
     WOLFSSL_P521_KYBER_LEVEL5},
16847
    {CURVE_NAME("X25519_KYBER_LEVEL1"), WOLFSSL_X25519_KYBER_LEVEL1,
16848
     WOLFSSL_X25519_KYBER_LEVEL1},
16849
    {CURVE_NAME("X448_KYBER_LEVEL3"), WOLFSSL_X448_KYBER_LEVEL3,
16850
     WOLFSSL_X448_KYBER_LEVEL3},
16851
    {CURVE_NAME("X25519_KYBER_LEVEL3"), WOLFSSL_X25519_KYBER_LEVEL3,
16852
     WOLFSSL_X25519_KYBER_LEVEL3},
16853
#endif
16854
#endif /* WOLFSSL_MLKEM_KYBER */
16855
#endif /* WOLFSSL_HAVE_MLKEM */
16856
#ifdef WOLFSSL_SM2
16857
    {CURVE_NAME("SM2"),     WC_NID_sm2, WOLFSSL_ECC_SM2P256V1},
16858
#endif
16859
#ifdef HAVE_ECC
16860
    /* Alternative curve names */
16861
    {CURVE_NAME("prime256v1"), WC_NID_X9_62_prime256v1, WOLFSSL_ECC_SECP256R1},
16862
    {CURVE_NAME("secp256r1"),  WC_NID_X9_62_prime256v1, WOLFSSL_ECC_SECP256R1},
16863
    {CURVE_NAME("secp384r1"),  WC_NID_secp384r1, WOLFSSL_ECC_SECP384R1},
16864
    {CURVE_NAME("secp521r1"),  WC_NID_secp521r1, WOLFSSL_ECC_SECP521R1},
16865
#endif
16866
#ifdef WOLFSSL_SM2
16867
    {CURVE_NAME("sm2p256v1"),  WC_NID_sm2, WOLFSSL_ECC_SM2P256V1},
16868
#endif
16869
    {0, NULL, 0, 0},
16870
};
16871
16872
int set_curves_list(WOLFSSL* ssl, WOLFSSL_CTX *ctx, const char* names,
16873
        byte curves_only)
16874
0
{
16875
0
    int idx, start = 0, len, i, ret = WOLFSSL_FAILURE;
16876
0
    word16 curve;
16877
0
    word32 disabled;
16878
0
    char name[MAX_CURVE_NAME_SZ];
16879
0
    byte groups_len = 0;
16880
0
#ifdef WOLFSSL_SMALL_STACK
16881
0
    void *heap = ssl? ssl->heap : ctx ? ctx->heap : NULL;
16882
0
    int *groups;
16883
#else
16884
    int groups[WOLFSSL_MAX_GROUP_COUNT];
16885
#endif
16886
0
    const WOLF_EC_NIST_NAME* nist_name;
16887
16888
0
    WC_ALLOC_VAR_EX(groups, int, WOLFSSL_MAX_GROUP_COUNT, heap,
16889
0
        DYNAMIC_TYPE_TMP_BUFFER,
16890
0
    {
16891
0
        ret=MEMORY_E;
16892
0
        goto leave;
16893
0
    });
16894
16895
0
    for (idx = 1; names[idx-1] != '\0'; idx++) {
16896
0
        if (names[idx] != ':' && names[idx] != '\0')
16897
0
            continue;
16898
16899
0
        len = idx - start;
16900
0
        if (len > MAX_CURVE_NAME_SZ - 1)
16901
0
            goto leave;
16902
16903
0
        XMEMCPY(name, names + start, (size_t)len);
16904
0
        name[len] = 0;
16905
0
        curve = WOLFSSL_NAMED_GROUP_INVALID;
16906
16907
0
        for (nist_name = kNistCurves; nist_name->name != NULL; nist_name++) {
16908
0
            if (len == nist_name->name_len &&
16909
0
                    XSTRNCMP(name, nist_name->name, (size_t)len) == 0) {
16910
0
                curve = nist_name->curve;
16911
0
                break;
16912
0
            }
16913
0
        }
16914
16915
0
        if (curve == WOLFSSL_NAMED_GROUP_INVALID) {
16916
0
        #if !defined(HAVE_FIPS) && !defined(HAVE_SELFTEST) && defined(HAVE_ECC)
16917
0
            int   nret;
16918
0
            const ecc_set_type *eccSet;
16919
16920
0
            nret = wc_ecc_get_curve_idx_from_name(name);
16921
0
            if (nret < 0) {
16922
0
                WOLFSSL_MSG("Could not find name in set");
16923
0
                goto leave;
16924
0
            }
16925
16926
0
            eccSet = wc_ecc_get_curve_params(ret);
16927
0
            if (eccSet == NULL) {
16928
0
                WOLFSSL_MSG("NULL set returned");
16929
0
                goto leave;
16930
0
            }
16931
16932
0
            curve = GetCurveByOID((int)eccSet->oidSum);
16933
        #else
16934
            WOLFSSL_MSG("API not present to search farther using name");
16935
            goto leave;
16936
        #endif
16937
0
        }
16938
16939
0
        if ((curves_only && curve >= WOLFSSL_ECC_MAX_AVAIL) ||
16940
0
                curve == WOLFSSL_NAMED_GROUP_INVALID) {
16941
0
            WOLFSSL_MSG("curve value is not supported");
16942
0
            goto leave;
16943
0
        }
16944
16945
0
        for (i = 0; i < groups_len; ++i) {
16946
0
            if (groups[i] == curve) {
16947
                /* silently drop duplicates */
16948
0
                break;
16949
0
            }
16950
0
        }
16951
0
        if (i >= groups_len) {
16952
0
            if (groups_len >= WOLFSSL_MAX_GROUP_COUNT) {
16953
0
                WOLFSSL_MSG_EX("setting %d or more supported "
16954
0
                               "curves is not permitted", groups_len);
16955
0
                goto leave;
16956
0
            }
16957
0
            groups[groups_len++] = (int)curve;
16958
0
        }
16959
16960
0
        start = idx + 1;
16961
0
    }
16962
16963
    /* Disable all curves so that only the ones the user wants are enabled. */
16964
0
    disabled = 0xFFFFFFFFUL;
16965
0
    for (i = 0; i < groups_len; ++i) {
16966
        /* Switch the bit to off and therefore is enabled. */
16967
0
        curve = (word16)groups[i];
16968
0
        if (curve >= 64) {
16969
0
            WC_DO_NOTHING;
16970
0
        }
16971
0
        else if (curve >= 32) {
16972
            /* 0 is for invalid and 1-14 aren't used otherwise. */
16973
0
            disabled &= ~(1U << (curve - 32));
16974
0
        }
16975
0
        else {
16976
0
            disabled &= ~(1U << curve);
16977
0
        }
16978
0
    #if defined(HAVE_SUPPORTED_CURVES) && !defined(NO_TLS)
16979
0
    #if !defined(WOLFSSL_OLD_SET_CURVES_LIST)
16980
        /* using the wolfSSL API to set the groups, this will populate
16981
         * (ssl|ctx)->groups and reset any TLSX_SUPPORTED_GROUPS.
16982
         * The order in (ssl|ctx)->groups will then be respected
16983
         * when TLSX_KEY_SHARE needs to be established */
16984
0
        if ((ssl && wolfSSL_set_groups(ssl, groups, groups_len)
16985
0
                        != WOLFSSL_SUCCESS)
16986
0
            || (ctx && wolfSSL_CTX_set_groups(ctx, groups, groups_len)
16987
0
                           != WOLFSSL_SUCCESS)) {
16988
0
            WOLFSSL_MSG("Unable to set supported curve");
16989
0
            goto leave;
16990
0
        }
16991
    #elif !defined(NO_WOLFSSL_CLIENT)
16992
        /* set the supported curve so client TLS extension contains only the
16993
         * desired curves */
16994
        if ((ssl && wolfSSL_UseSupportedCurve(ssl, curve) != WOLFSSL_SUCCESS)
16995
            || (ctx && wolfSSL_CTX_UseSupportedCurve(ctx, curve)
16996
                           != WOLFSSL_SUCCESS)) {
16997
            WOLFSSL_MSG("Unable to set supported curve");
16998
            goto leave;
16999
        }
17000
    #endif
17001
0
    #endif /* HAVE_SUPPORTED_CURVES && !NO_TLS */
17002
0
    }
17003
17004
0
    if (ssl != NULL)
17005
0
        ssl->disabledCurves = disabled;
17006
0
    else if (ctx != NULL)
17007
0
        ctx->disabledCurves = disabled;
17008
0
    ret = WOLFSSL_SUCCESS;
17009
17010
0
leave:
17011
0
#ifdef WOLFSSL_SMALL_STACK
17012
0
    if (groups)
17013
0
        XFREE((void*)groups, heap, DYNAMIC_TYPE_TMP_BUFFER);
17014
0
#endif
17015
0
    return ret;
17016
0
}
17017
17018
int wolfSSL_CTX_set1_curves_list(WOLFSSL_CTX* ctx, const char* names)
17019
0
{
17020
0
    WOLFSSL_ENTER("wolfSSL_CTX_set1_curves_list");
17021
0
    if (ctx == NULL || names == NULL) {
17022
0
        WOLFSSL_MSG("ctx or names was NULL");
17023
0
        return WOLFSSL_FAILURE;
17024
0
    }
17025
0
    return set_curves_list(NULL, ctx, names, 1);
17026
0
}
17027
17028
int wolfSSL_set1_curves_list(WOLFSSL* ssl, const char* names)
17029
0
{
17030
0
    WOLFSSL_ENTER("wolfSSL_set1_curves_list");
17031
0
    if (ssl == NULL || names == NULL) {
17032
0
        WOLFSSL_MSG("ssl or names was NULL");
17033
0
        return WOLFSSL_FAILURE;
17034
0
    }
17035
0
    return set_curves_list(ssl, NULL, names, 1);
17036
0
}
17037
#endif /* (HAVE_ECC || HAVE_CURVE25519 || HAVE_CURVE448) */
17038
#endif /* OPENSSL_EXTRA || HAVE_CURL */
17039
17040
17041
#ifdef OPENSSL_EXTRA
17042
/* Sets a callback for when sending and receiving protocol messages.
17043
 * This callback is copied to all WOLFSSL objects created from the ctx.
17044
 *
17045
 * ctx WOLFSSL_CTX structure to set callback in
17046
 * cb  callback to use
17047
 *
17048
 * return WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE with error case
17049
 */
17050
int wolfSSL_CTX_set_msg_callback(WOLFSSL_CTX *ctx, SSL_Msg_Cb cb)
17051
0
{
17052
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_msg_callback");
17053
0
    if (ctx == NULL) {
17054
0
        WOLFSSL_MSG("Null ctx passed in");
17055
0
        return WOLFSSL_FAILURE;
17056
0
    }
17057
17058
0
    ctx->protoMsgCb = cb;
17059
0
    return WOLFSSL_SUCCESS;
17060
0
}
17061
17062
17063
/* Sets a callback for when sending and receiving protocol messages.
17064
 *
17065
 * ssl WOLFSSL structure to set callback in
17066
 * cb  callback to use
17067
 *
17068
 * return WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE with error case
17069
 */
17070
int wolfSSL_set_msg_callback(WOLFSSL *ssl, SSL_Msg_Cb cb)
17071
0
{
17072
0
    WOLFSSL_ENTER("wolfSSL_set_msg_callback");
17073
17074
0
    if (ssl == NULL) {
17075
0
        return WOLFSSL_FAILURE;
17076
0
    }
17077
17078
0
    if (cb != NULL) {
17079
0
        ssl->toInfoOn = 1;
17080
0
    }
17081
17082
0
    ssl->protoMsgCb = cb;
17083
0
    return WOLFSSL_SUCCESS;
17084
0
}
17085
17086
17087
/* set the user argument to pass to the msg callback when called
17088
 * return WOLFSSL_SUCCESS on success */
17089
int wolfSSL_CTX_set_msg_callback_arg(WOLFSSL_CTX *ctx, void* arg)
17090
0
{
17091
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_msg_callback_arg");
17092
0
    if (ctx == NULL) {
17093
0
        WOLFSSL_MSG("Null WOLFSSL_CTX passed in");
17094
0
        return WOLFSSL_FAILURE;
17095
0
    }
17096
17097
0
    ctx->protoMsgCtx = arg;
17098
0
    return WOLFSSL_SUCCESS;
17099
0
}
17100
17101
17102
int wolfSSL_set_msg_callback_arg(WOLFSSL *ssl, void* arg)
17103
0
{
17104
0
    WOLFSSL_ENTER("wolfSSL_set_msg_callback_arg");
17105
0
    if (ssl == NULL)
17106
0
        return WOLFSSL_FAILURE;
17107
17108
0
    ssl->protoMsgCtx = arg;
17109
0
    return WOLFSSL_SUCCESS;
17110
0
}
17111
17112
void *wolfSSL_OPENSSL_memdup(const void *data, size_t siz, const char* file,
17113
    int line)
17114
0
{
17115
0
    void *ret;
17116
0
    (void)file;
17117
0
    (void)line;
17118
17119
0
    if (data == NULL || siz >= INT_MAX)
17120
0
        return NULL;
17121
17122
0
    ret = wolfSSL_OPENSSL_malloc(siz);
17123
0
    if (ret == NULL) {
17124
0
        return NULL;
17125
0
    }
17126
0
    return XMEMCPY(ret, data, siz);
17127
0
}
17128
17129
void wolfSSL_OPENSSL_cleanse(void *ptr, size_t len)
17130
0
{
17131
0
    if (ptr)
17132
0
        ForceZero(ptr, (word32)len);
17133
0
}
17134
17135
int wolfSSL_CTX_set_alpn_protos(WOLFSSL_CTX *ctx, const unsigned char *p,
17136
                            unsigned int p_len)
17137
0
{
17138
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_alpn_protos");
17139
0
    if (ctx == NULL)
17140
0
        return BAD_FUNC_ARG;
17141
0
    if (ctx->alpn_cli_protos != NULL) {
17142
0
        XFREE((void*)ctx->alpn_cli_protos, ctx->heap, DYNAMIC_TYPE_OPENSSL);
17143
0
    }
17144
17145
0
    ctx->alpn_cli_protos = (const unsigned char*)XMALLOC(p_len,
17146
0
        ctx->heap, DYNAMIC_TYPE_OPENSSL);
17147
0
    if (ctx->alpn_cli_protos == NULL) {
17148
0
#if defined(WOLFSSL_ERROR_CODE_OPENSSL)
17149
        /* 0 on success in OpenSSL, non-0 on failure in OpenSSL
17150
         * the function reverses the return value convention.
17151
         */
17152
0
        return 1;
17153
#else
17154
        return WOLFSSL_FAILURE;
17155
#endif
17156
0
    }
17157
0
    XMEMCPY((void*)ctx->alpn_cli_protos, p, p_len);
17158
0
    ctx->alpn_cli_protos_len = p_len;
17159
17160
0
#if defined(WOLFSSL_ERROR_CODE_OPENSSL)
17161
    /* 0 on success in OpenSSL, non-0 on failure in OpenSSL
17162
     * the function reverses the return value convention.
17163
     */
17164
0
    return 0;
17165
#else
17166
    return WOLFSSL_SUCCESS;
17167
#endif
17168
0
}
17169
17170
17171
#ifdef HAVE_ALPN
17172
#ifndef NO_BIO
17173
/* Sets the ALPN extension protos
17174
 *
17175
 * example format is
17176
 * unsigned char p[] = {
17177
 *      8, 'h', 't', 't', 'p', '/', '1', '.', '1'
17178
 * };
17179
 *
17180
 * returns WOLFSSL_SUCCESS on success */
17181
int wolfSSL_set_alpn_protos(WOLFSSL* ssl,
17182
        const unsigned char* p, unsigned int p_len)
17183
{
17184
    char* pt = NULL;
17185
    unsigned int ptIdx;
17186
    unsigned int sz;
17187
    unsigned int idx = 0;
17188
    int alpn_opt = WOLFSSL_ALPN_CONTINUE_ON_MISMATCH;
17189
    int ret;
17190
17191
    WOLFSSL_ENTER("wolfSSL_set_alpn_protos");
17192
17193
    if (ssl == NULL || p_len <= 1) {
17194
#if defined(WOLFSSL_ERROR_CODE_OPENSSL)
17195
        /* 0 on success in OpenSSL, non-0 on failure in OpenSSL
17196
         * the function reverses the return value convention.
17197
         */
17198
        return 1;
17199
#else
17200
        return WOLFSSL_FAILURE;
17201
#endif
17202
    }
17203
17204
    /* Replacing leading number with trailing ',' and adding '\0'. */
17205
    pt = (char*)XMALLOC(p_len + 1, ssl->heap, DYNAMIC_TYPE_OPENSSL);
17206
    if (pt == NULL) {
17207
#if defined(WOLFSSL_ERROR_CODE_OPENSSL)
17208
        /* 0 on success in OpenSSL, non-0 on failure in OpenSSL
17209
         * the function reverses the return value convention.
17210
         */
17211
        return 1;
17212
#else
17213
        return WOLFSSL_FAILURE;
17214
#endif
17215
    }
17216
17217
    ptIdx = 0;
17218
    /* convert into comma separated list */
17219
    while (idx < p_len - 1) {
17220
        unsigned int i;
17221
17222
        sz = p[idx++];
17223
        if (idx + sz > p_len) {
17224
            WOLFSSL_MSG("Bad list format");
17225
            XFREE(pt, ssl->heap, DYNAMIC_TYPE_OPENSSL);
17226
    #if defined(WOLFSSL_ERROR_CODE_OPENSSL)
17227
            /* 0 on success in OpenSSL, non-0 on failure in OpenSSL
17228
             * the function reverses the return value convention.
17229
             */
17230
            return 1;
17231
    #else
17232
            return WOLFSSL_FAILURE;
17233
    #endif
17234
        }
17235
        if (sz > 0) {
17236
            for (i = 0; i < sz; i++) {
17237
                pt[ptIdx++] = p[idx++];
17238
            }
17239
            if (idx < p_len - 1) {
17240
                pt[ptIdx++] = ',';
17241
            }
17242
        }
17243
    }
17244
    pt[ptIdx++] = '\0';
17245
17246
    /* clears out all current ALPN extensions set */
17247
    TLSX_Remove(&ssl->extensions, TLSX_APPLICATION_LAYER_PROTOCOL, ssl->heap);
17248
17249
    ret = wolfSSL_UseALPN(ssl, pt, ptIdx, (byte)alpn_opt);
17250
    XFREE(pt, ssl->heap, DYNAMIC_TYPE_OPENSSL);
17251
#if defined(WOLFSSL_ERROR_CODE_OPENSSL)
17252
    /* 0 on success in OpenSSL, non-0 on failure in OpenSSL
17253
     * the function reverses the return value convention.
17254
     */
17255
    if (ret != WOLFSSL_SUCCESS)
17256
        return 1;
17257
    return 0;
17258
#else
17259
    if (ret != WOLFSSL_SUCCESS)
17260
        return WOLFSSL_FAILURE;
17261
    return WOLFSSL_SUCCESS;
17262
#endif
17263
}
17264
#endif /* !NO_BIO */
17265
#endif /* HAVE_ALPN */
17266
#endif /* OPENSSL_EXTRA */
17267
17268
#if defined(OPENSSL_EXTRA)
17269
17270
#ifndef NO_BIO
17271
#define WOLFSSL_BIO_INCLUDED
17272
#include "src/bio.c"
17273
#endif
17274
17275
#endif /* OPENSSL_EXTRA */
17276
17277
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
17278
17279
word32 nid2oid(int nid, int grp)
17280
0
{
17281
    /* get OID type */
17282
0
    switch (grp) {
17283
        /* oidHashType */
17284
0
        case oidHashType:
17285
0
            switch (nid) {
17286
0
            #ifdef WOLFSSL_MD2
17287
0
                case WC_NID_md2:
17288
0
                    return MD2h;
17289
0
            #endif
17290
0
            #ifndef NO_MD5
17291
0
                case WC_NID_md5:
17292
0
                    return MD5h;
17293
0
            #endif
17294
0
            #ifndef NO_SHA
17295
0
                case WC_NID_sha1:
17296
0
                    return SHAh;
17297
0
            #endif
17298
0
                case WC_NID_sha224:
17299
0
                    return SHA224h;
17300
0
            #ifndef NO_SHA256
17301
0
                case WC_NID_sha256:
17302
0
                    return SHA256h;
17303
0
            #endif
17304
0
            #ifdef WOLFSSL_SHA384
17305
0
                case WC_NID_sha384:
17306
0
                    return SHA384h;
17307
0
            #endif
17308
0
            #ifdef WOLFSSL_SHA512
17309
0
                case WC_NID_sha512:
17310
0
                    return SHA512h;
17311
0
            #endif
17312
0
            #ifndef WOLFSSL_NOSHA3_224
17313
0
                case WC_NID_sha3_224:
17314
0
                    return SHA3_224h;
17315
0
            #endif
17316
0
            #ifndef WOLFSSL_NOSHA3_256
17317
0
                case WC_NID_sha3_256:
17318
0
                    return SHA3_256h;
17319
0
            #endif
17320
0
            #ifndef WOLFSSL_NOSHA3_384
17321
0
                case WC_NID_sha3_384:
17322
0
                    return SHA3_384h;
17323
0
            #endif
17324
0
            #ifndef WOLFSSL_NOSHA3_512
17325
0
                case WC_NID_sha3_512:
17326
0
                    return SHA3_512h;
17327
0
            #endif
17328
0
            }
17329
0
            break;
17330
17331
        /*  oidSigType */
17332
0
        case oidSigType:
17333
0
            switch (nid) {
17334
            #ifndef NO_DSA
17335
                case WC_NID_dsaWithSHA1:
17336
                    return CTC_SHAwDSA;
17337
                case WC_NID_dsa_with_SHA256:
17338
                    return CTC_SHA256wDSA;
17339
            #endif /* NO_DSA */
17340
0
            #ifndef NO_RSA
17341
0
                case WC_NID_md2WithRSAEncryption:
17342
0
                    return CTC_MD2wRSA;
17343
0
                case WC_NID_md5WithRSAEncryption:
17344
0
                    return CTC_MD5wRSA;
17345
0
                case WC_NID_sha1WithRSAEncryption:
17346
0
                    return CTC_SHAwRSA;
17347
0
                case WC_NID_sha224WithRSAEncryption:
17348
0
                    return CTC_SHA224wRSA;
17349
0
                case WC_NID_sha256WithRSAEncryption:
17350
0
                    return CTC_SHA256wRSA;
17351
0
                case WC_NID_sha384WithRSAEncryption:
17352
0
                    return CTC_SHA384wRSA;
17353
0
                case WC_NID_sha512WithRSAEncryption:
17354
0
                    return CTC_SHA512wRSA;
17355
0
                #ifdef WOLFSSL_SHA3
17356
0
                case WC_NID_RSA_SHA3_224:
17357
0
                    return CTC_SHA3_224wRSA;
17358
0
                case WC_NID_RSA_SHA3_256:
17359
0
                    return CTC_SHA3_256wRSA;
17360
0
                case WC_NID_RSA_SHA3_384:
17361
0
                    return CTC_SHA3_384wRSA;
17362
0
                case WC_NID_RSA_SHA3_512:
17363
0
                    return CTC_SHA3_512wRSA;
17364
0
                #endif
17365
0
            #endif /* NO_RSA */
17366
0
            #ifdef HAVE_ECC
17367
0
                case WC_NID_ecdsa_with_SHA1:
17368
0
                    return CTC_SHAwECDSA;
17369
0
                case WC_NID_ecdsa_with_SHA224:
17370
0
                    return CTC_SHA224wECDSA;
17371
0
                case WC_NID_ecdsa_with_SHA256:
17372
0
                    return CTC_SHA256wECDSA;
17373
0
                case WC_NID_ecdsa_with_SHA384:
17374
0
                    return CTC_SHA384wECDSA;
17375
0
                case WC_NID_ecdsa_with_SHA512:
17376
0
                    return CTC_SHA512wECDSA;
17377
0
                #ifdef WOLFSSL_SHA3
17378
0
                case WC_NID_ecdsa_with_SHA3_224:
17379
0
                    return CTC_SHA3_224wECDSA;
17380
0
                case WC_NID_ecdsa_with_SHA3_256:
17381
0
                    return CTC_SHA3_256wECDSA;
17382
0
                case WC_NID_ecdsa_with_SHA3_384:
17383
0
                    return CTC_SHA3_384wECDSA;
17384
0
                case WC_NID_ecdsa_with_SHA3_512:
17385
0
                    return CTC_SHA3_512wECDSA;
17386
0
                #endif
17387
0
            #endif /* HAVE_ECC */
17388
0
            }
17389
0
            break;
17390
17391
        /* oidKeyType */
17392
0
        case oidKeyType:
17393
0
            switch (nid) {
17394
            #ifndef NO_DSA
17395
                case WC_NID_dsa:
17396
                    return DSAk;
17397
            #endif /* NO_DSA */
17398
0
            #ifndef NO_RSA
17399
0
                case WC_NID_rsaEncryption:
17400
0
                    return RSAk;
17401
0
            #endif /* NO_RSA */
17402
0
            #ifdef HAVE_ECC
17403
0
                case WC_NID_X9_62_id_ecPublicKey:
17404
0
                    return ECDSAk;
17405
0
            #endif /* HAVE_ECC */
17406
0
            }
17407
0
            break;
17408
17409
17410
0
    #ifdef HAVE_ECC
17411
0
        case oidCurveType:
17412
0
            switch (nid) {
17413
0
            case WC_NID_X9_62_prime192v1:
17414
0
                return ECC_SECP192R1_OID;
17415
0
            case WC_NID_X9_62_prime192v2:
17416
0
                return ECC_PRIME192V2_OID;
17417
0
            case WC_NID_X9_62_prime192v3:
17418
0
                return ECC_PRIME192V3_OID;
17419
0
            case WC_NID_X9_62_prime239v1:
17420
0
                return ECC_PRIME239V1_OID;
17421
0
            case WC_NID_X9_62_prime239v2:
17422
0
                return ECC_PRIME239V2_OID;
17423
0
            case WC_NID_X9_62_prime239v3:
17424
0
                return ECC_PRIME239V3_OID;
17425
0
            case WC_NID_X9_62_prime256v1:
17426
0
                return ECC_SECP256R1_OID;
17427
0
            case WC_NID_secp112r1:
17428
0
                return ECC_SECP112R1_OID;
17429
0
            case WC_NID_secp112r2:
17430
0
                return ECC_SECP112R2_OID;
17431
0
            case WC_NID_secp128r1:
17432
0
                return ECC_SECP128R1_OID;
17433
0
            case WC_NID_secp128r2:
17434
0
                return ECC_SECP128R2_OID;
17435
0
            case WC_NID_secp160r1:
17436
0
                return ECC_SECP160R1_OID;
17437
0
            case WC_NID_secp160r2:
17438
0
                return ECC_SECP160R2_OID;
17439
0
            case WC_NID_secp224r1:
17440
0
                return ECC_SECP224R1_OID;
17441
0
            case WC_NID_secp384r1:
17442
0
                return ECC_SECP384R1_OID;
17443
0
            case WC_NID_secp521r1:
17444
0
                return ECC_SECP521R1_OID;
17445
0
            case WC_NID_secp160k1:
17446
0
                return ECC_SECP160K1_OID;
17447
0
            case WC_NID_secp192k1:
17448
0
                return ECC_SECP192K1_OID;
17449
0
            case WC_NID_secp224k1:
17450
0
                return ECC_SECP224K1_OID;
17451
0
            case WC_NID_secp256k1:
17452
0
                return ECC_SECP256K1_OID;
17453
0
            case WC_NID_brainpoolP160r1:
17454
0
                return ECC_BRAINPOOLP160R1_OID;
17455
0
            case WC_NID_brainpoolP192r1:
17456
0
                return ECC_BRAINPOOLP192R1_OID;
17457
0
            case WC_NID_brainpoolP224r1:
17458
0
                return ECC_BRAINPOOLP224R1_OID;
17459
0
            case WC_NID_brainpoolP256r1:
17460
0
                return ECC_BRAINPOOLP256R1_OID;
17461
0
            case WC_NID_brainpoolP320r1:
17462
0
                return ECC_BRAINPOOLP320R1_OID;
17463
0
            case WC_NID_brainpoolP384r1:
17464
0
                return ECC_BRAINPOOLP384R1_OID;
17465
0
            case WC_NID_brainpoolP512r1:
17466
0
                return ECC_BRAINPOOLP512R1_OID;
17467
0
            }
17468
0
            break;
17469
0
    #endif /* HAVE_ECC */
17470
17471
        /* oidBlkType */
17472
0
        case oidBlkType:
17473
0
            switch (nid) {
17474
0
            #ifdef WOLFSSL_AES_128
17475
0
                case AES128CBCb:
17476
0
                    return AES128CBCb;
17477
0
            #endif
17478
0
            #ifdef WOLFSSL_AES_192
17479
0
                case AES192CBCb:
17480
0
                    return AES192CBCb;
17481
0
            #endif
17482
0
            #ifdef WOLFSSL_AES_256
17483
0
                case AES256CBCb:
17484
0
                    return AES256CBCb;
17485
0
            #endif
17486
0
            #ifndef NO_DES3
17487
0
                case WC_NID_des:
17488
0
                    return DESb;
17489
0
                case WC_NID_des3:
17490
0
                    return DES3b;
17491
0
            #endif
17492
0
            }
17493
0
            break;
17494
17495
0
    #ifdef HAVE_OCSP
17496
0
        case oidOcspType:
17497
0
            switch (nid) {
17498
0
                case WC_NID_id_pkix_OCSP_basic:
17499
0
                    return OCSP_BASIC_OID;
17500
0
                case OCSP_NONCE_OID:
17501
0
                    return OCSP_NONCE_OID;
17502
0
            }
17503
0
            break;
17504
0
    #endif /* HAVE_OCSP */
17505
17506
        /* oidCertExtType */
17507
0
        case oidCertExtType:
17508
0
            switch (nid) {
17509
0
                case WC_NID_basic_constraints:
17510
0
                    return BASIC_CA_OID;
17511
0
                case WC_NID_subject_alt_name:
17512
0
                    return ALT_NAMES_OID;
17513
0
                case WC_NID_crl_distribution_points:
17514
0
                    return CRL_DIST_OID;
17515
0
                case WC_NID_info_access:
17516
0
                    return AUTH_INFO_OID;
17517
0
                case WC_NID_authority_key_identifier:
17518
0
                    return AUTH_KEY_OID;
17519
0
                case WC_NID_subject_key_identifier:
17520
0
                    return SUBJ_KEY_OID;
17521
0
                case WC_NID_inhibit_any_policy:
17522
0
                    return INHIBIT_ANY_OID;
17523
0
                case WC_NID_key_usage:
17524
0
                    return KEY_USAGE_OID;
17525
0
                case WC_NID_name_constraints:
17526
0
                    return NAME_CONS_OID;
17527
0
                case WC_NID_certificate_policies:
17528
0
                    return CERT_POLICY_OID;
17529
0
                case WC_NID_ext_key_usage:
17530
0
                    return EXT_KEY_USAGE_OID;
17531
0
            }
17532
0
            break;
17533
17534
        /* oidCertAuthInfoType */
17535
0
        case oidCertAuthInfoType:
17536
0
            switch (nid) {
17537
0
                case WC_NID_ad_OCSP:
17538
0
                    return AIA_OCSP_OID;
17539
0
                case WC_NID_ad_ca_issuers:
17540
0
                    return AIA_CA_ISSUER_OID;
17541
0
            }
17542
0
            break;
17543
17544
        /* oidCertPolicyType */
17545
0
        case oidCertPolicyType:
17546
0
            switch (nid) {
17547
0
                case WC_NID_any_policy:
17548
0
                    return CP_ANY_OID;
17549
0
            }
17550
0
            break;
17551
17552
        /* oidCertAltNameType */
17553
0
        case oidCertAltNameType:
17554
0
            switch (nid) {
17555
0
                case WC_NID_hw_name_oid:
17556
0
                    return HW_NAME_OID;
17557
0
            }
17558
0
            break;
17559
17560
        /* oidCertKeyUseType */
17561
0
        case oidCertKeyUseType:
17562
0
            switch (nid) {
17563
0
                case WC_NID_anyExtendedKeyUsage:
17564
0
                    return EKU_ANY_OID;
17565
0
                case EKU_SERVER_AUTH_OID:
17566
0
                    return EKU_SERVER_AUTH_OID;
17567
0
                case EKU_CLIENT_AUTH_OID:
17568
0
                    return EKU_CLIENT_AUTH_OID;
17569
0
                case EKU_OCSP_SIGN_OID:
17570
0
                    return EKU_OCSP_SIGN_OID;
17571
0
            }
17572
0
            break;
17573
17574
        /* oidKdfType */
17575
0
        case oidKdfType:
17576
0
            switch (nid) {
17577
0
                case PBKDF2_OID:
17578
0
                    return PBKDF2_OID;
17579
0
            }
17580
0
            break;
17581
17582
        /* oidPBEType */
17583
0
        case oidPBEType:
17584
0
            switch (nid) {
17585
0
                case PBE_SHA1_RC4_128:
17586
0
                    return PBE_SHA1_RC4_128;
17587
0
                case PBE_SHA1_DES:
17588
0
                    return PBE_SHA1_DES;
17589
0
                case PBE_SHA1_DES3:
17590
0
                    return PBE_SHA1_DES3;
17591
0
            }
17592
0
            break;
17593
17594
        /* oidKeyWrapType */
17595
0
        case oidKeyWrapType:
17596
0
            switch (nid) {
17597
0
            #ifdef WOLFSSL_AES_128
17598
0
                case AES128_WRAP:
17599
0
                    return AES128_WRAP;
17600
0
            #endif
17601
0
            #ifdef WOLFSSL_AES_192
17602
0
                case AES192_WRAP:
17603
0
                    return AES192_WRAP;
17604
0
            #endif
17605
0
            #ifdef WOLFSSL_AES_256
17606
0
                case AES256_WRAP:
17607
0
                    return AES256_WRAP;
17608
0
            #endif
17609
0
            }
17610
0
            break;
17611
17612
        /* oidCmsKeyAgreeType */
17613
0
        case oidCmsKeyAgreeType:
17614
0
            switch (nid) {
17615
0
                #ifndef NO_SHA
17616
0
                case dhSinglePass_stdDH_sha1kdf_scheme:
17617
0
                    return dhSinglePass_stdDH_sha1kdf_scheme;
17618
0
                #endif
17619
0
                #ifdef WOLFSSL_SHA224
17620
0
                case dhSinglePass_stdDH_sha224kdf_scheme:
17621
0
                    return dhSinglePass_stdDH_sha224kdf_scheme;
17622
0
                #endif
17623
0
                #ifndef NO_SHA256
17624
0
                case dhSinglePass_stdDH_sha256kdf_scheme:
17625
0
                    return dhSinglePass_stdDH_sha256kdf_scheme;
17626
0
                #endif
17627
0
                #ifdef WOLFSSL_SHA384
17628
0
                case dhSinglePass_stdDH_sha384kdf_scheme:
17629
0
                    return dhSinglePass_stdDH_sha384kdf_scheme;
17630
0
                #endif
17631
0
                #ifdef WOLFSSL_SHA512
17632
0
                case dhSinglePass_stdDH_sha512kdf_scheme:
17633
0
                    return dhSinglePass_stdDH_sha512kdf_scheme;
17634
0
                #endif
17635
0
            }
17636
0
            break;
17637
17638
        /* oidCmsKeyAgreeType */
17639
    #ifdef WOLFSSL_CERT_REQ
17640
        case oidCsrAttrType:
17641
            switch (nid) {
17642
                case WC_NID_pkcs9_contentType:
17643
                    return PKCS9_CONTENT_TYPE_OID;
17644
                case WC_NID_pkcs9_challengePassword:
17645
                    return CHALLENGE_PASSWORD_OID;
17646
                case WC_NID_serialNumber:
17647
                    return SERIAL_NUMBER_OID;
17648
                case WC_NID_userId:
17649
                    return USER_ID_OID;
17650
                case WC_NID_surname:
17651
                    return SURNAME_OID;
17652
            }
17653
            break;
17654
    #endif
17655
17656
0
        default:
17657
0
            WOLFSSL_MSG("NID not in table");
17658
            /* MSVC warns without the cast */
17659
0
            return (word32)-1;
17660
0
    }
17661
17662
    /* MSVC warns without the cast */
17663
0
    return (word32)-1;
17664
0
}
17665
17666
int oid2nid(word32 oid, int grp)
17667
0
{
17668
0
    size_t i;
17669
    /* get OID type */
17670
0
    switch (grp) {
17671
        /* oidHashType */
17672
0
        case oidHashType:
17673
0
            switch (oid) {
17674
0
            #ifdef WOLFSSL_MD2
17675
0
                case MD2h:
17676
0
                    return WC_NID_md2;
17677
0
            #endif
17678
0
            #ifndef NO_MD5
17679
0
                case MD5h:
17680
0
                    return WC_NID_md5;
17681
0
            #endif
17682
0
            #ifndef NO_SHA
17683
0
                case SHAh:
17684
0
                    return WC_NID_sha1;
17685
0
            #endif
17686
0
                case SHA224h:
17687
0
                    return WC_NID_sha224;
17688
0
            #ifndef NO_SHA256
17689
0
                case SHA256h:
17690
0
                    return WC_NID_sha256;
17691
0
            #endif
17692
0
            #ifdef WOLFSSL_SHA384
17693
0
                case SHA384h:
17694
0
                    return WC_NID_sha384;
17695
0
            #endif
17696
0
            #ifdef WOLFSSL_SHA512
17697
0
                case SHA512h:
17698
0
                    return WC_NID_sha512;
17699
0
            #endif
17700
0
            }
17701
0
            break;
17702
17703
        /*  oidSigType */
17704
0
        case oidSigType:
17705
0
            switch (oid) {
17706
            #ifndef NO_DSA
17707
                case CTC_SHAwDSA:
17708
                    return WC_NID_dsaWithSHA1;
17709
                case CTC_SHA256wDSA:
17710
                    return WC_NID_dsa_with_SHA256;
17711
            #endif /* NO_DSA */
17712
0
            #ifndef NO_RSA
17713
0
                case CTC_MD2wRSA:
17714
0
                    return WC_NID_md2WithRSAEncryption;
17715
0
                case CTC_MD5wRSA:
17716
0
                    return WC_NID_md5WithRSAEncryption;
17717
0
                case CTC_SHAwRSA:
17718
0
                    return WC_NID_sha1WithRSAEncryption;
17719
0
                case CTC_SHA224wRSA:
17720
0
                    return WC_NID_sha224WithRSAEncryption;
17721
0
                case CTC_SHA256wRSA:
17722
0
                    return WC_NID_sha256WithRSAEncryption;
17723
0
                case CTC_SHA384wRSA:
17724
0
                    return WC_NID_sha384WithRSAEncryption;
17725
0
                case CTC_SHA512wRSA:
17726
0
                    return WC_NID_sha512WithRSAEncryption;
17727
0
                #ifdef WOLFSSL_SHA3
17728
0
                case CTC_SHA3_224wRSA:
17729
0
                    return WC_NID_RSA_SHA3_224;
17730
0
                case CTC_SHA3_256wRSA:
17731
0
                    return WC_NID_RSA_SHA3_256;
17732
0
                case CTC_SHA3_384wRSA:
17733
0
                    return WC_NID_RSA_SHA3_384;
17734
0
                case CTC_SHA3_512wRSA:
17735
0
                    return WC_NID_RSA_SHA3_512;
17736
0
                #endif
17737
0
                #ifdef WC_RSA_PSS
17738
0
                case CTC_RSASSAPSS:
17739
0
                    return WC_NID_rsassaPss;
17740
0
                #endif
17741
0
            #endif /* NO_RSA */
17742
0
            #ifdef HAVE_ECC
17743
0
                case CTC_SHAwECDSA:
17744
0
                    return WC_NID_ecdsa_with_SHA1;
17745
0
                case CTC_SHA224wECDSA:
17746
0
                    return WC_NID_ecdsa_with_SHA224;
17747
0
                case CTC_SHA256wECDSA:
17748
0
                    return WC_NID_ecdsa_with_SHA256;
17749
0
                case CTC_SHA384wECDSA:
17750
0
                    return WC_NID_ecdsa_with_SHA384;
17751
0
                case CTC_SHA512wECDSA:
17752
0
                    return WC_NID_ecdsa_with_SHA512;
17753
0
                #ifdef WOLFSSL_SHA3
17754
0
                case CTC_SHA3_224wECDSA:
17755
0
                    return WC_NID_ecdsa_with_SHA3_224;
17756
0
                case CTC_SHA3_256wECDSA:
17757
0
                    return WC_NID_ecdsa_with_SHA3_256;
17758
0
                case CTC_SHA3_384wECDSA:
17759
0
                    return WC_NID_ecdsa_with_SHA3_384;
17760
0
                case CTC_SHA3_512wECDSA:
17761
0
                    return WC_NID_ecdsa_with_SHA3_512;
17762
0
                #endif
17763
0
            #endif /* HAVE_ECC */
17764
0
            }
17765
0
            break;
17766
17767
        /* oidKeyType */
17768
0
        case oidKeyType:
17769
0
            switch (oid) {
17770
            #ifndef NO_DSA
17771
                case DSAk:
17772
                    return WC_NID_dsa;
17773
            #endif /* NO_DSA */
17774
0
            #ifndef NO_RSA
17775
0
                case RSAk:
17776
0
                    return WC_NID_rsaEncryption;
17777
0
                #ifdef WC_RSA_PSS
17778
0
                case RSAPSSk:
17779
0
                    return WC_NID_rsassaPss;
17780
0
                #endif
17781
0
            #endif /* NO_RSA */
17782
0
            #ifdef HAVE_ECC
17783
0
                case ECDSAk:
17784
0
                    return WC_NID_X9_62_id_ecPublicKey;
17785
0
            #endif /* HAVE_ECC */
17786
0
            }
17787
0
            break;
17788
17789
17790
0
    #ifdef HAVE_ECC
17791
0
        case oidCurveType:
17792
0
            switch (oid) {
17793
0
            case ECC_SECP192R1_OID:
17794
0
                return WC_NID_X9_62_prime192v1;
17795
0
            case ECC_PRIME192V2_OID:
17796
0
                return WC_NID_X9_62_prime192v2;
17797
0
            case ECC_PRIME192V3_OID:
17798
0
                return WC_NID_X9_62_prime192v3;
17799
0
            case ECC_PRIME239V1_OID:
17800
0
                return WC_NID_X9_62_prime239v1;
17801
0
            case ECC_PRIME239V2_OID:
17802
0
                return WC_NID_X9_62_prime239v2;
17803
0
            case ECC_PRIME239V3_OID:
17804
0
                return WC_NID_X9_62_prime239v3;
17805
0
            case ECC_SECP256R1_OID:
17806
0
                return WC_NID_X9_62_prime256v1;
17807
0
            case ECC_SECP112R1_OID:
17808
0
                return WC_NID_secp112r1;
17809
0
            case ECC_SECP112R2_OID:
17810
0
                return WC_NID_secp112r2;
17811
0
            case ECC_SECP128R1_OID:
17812
0
                return WC_NID_secp128r1;
17813
0
            case ECC_SECP128R2_OID:
17814
0
                return WC_NID_secp128r2;
17815
0
            case ECC_SECP160R1_OID:
17816
0
                return WC_NID_secp160r1;
17817
0
            case ECC_SECP160R2_OID:
17818
0
                return WC_NID_secp160r2;
17819
0
            case ECC_SECP224R1_OID:
17820
0
                return WC_NID_secp224r1;
17821
0
            case ECC_SECP384R1_OID:
17822
0
                return WC_NID_secp384r1;
17823
0
            case ECC_SECP521R1_OID:
17824
0
                return WC_NID_secp521r1;
17825
0
            case ECC_SECP160K1_OID:
17826
0
                return WC_NID_secp160k1;
17827
0
            case ECC_SECP192K1_OID:
17828
0
                return WC_NID_secp192k1;
17829
0
            case ECC_SECP224K1_OID:
17830
0
                return WC_NID_secp224k1;
17831
0
            case ECC_SECP256K1_OID:
17832
0
                return WC_NID_secp256k1;
17833
0
            case ECC_BRAINPOOLP160R1_OID:
17834
0
                return WC_NID_brainpoolP160r1;
17835
0
            case ECC_BRAINPOOLP192R1_OID:
17836
0
                return WC_NID_brainpoolP192r1;
17837
0
            case ECC_BRAINPOOLP224R1_OID:
17838
0
                return WC_NID_brainpoolP224r1;
17839
0
            case ECC_BRAINPOOLP256R1_OID:
17840
0
                return WC_NID_brainpoolP256r1;
17841
0
            case ECC_BRAINPOOLP320R1_OID:
17842
0
                return WC_NID_brainpoolP320r1;
17843
0
            case ECC_BRAINPOOLP384R1_OID:
17844
0
                return WC_NID_brainpoolP384r1;
17845
0
            case ECC_BRAINPOOLP512R1_OID:
17846
0
                return WC_NID_brainpoolP512r1;
17847
0
            }
17848
0
            break;
17849
0
    #endif /* HAVE_ECC */
17850
17851
        /* oidBlkType */
17852
0
        case oidBlkType:
17853
0
            switch (oid) {
17854
0
            #ifdef WOLFSSL_AES_128
17855
0
                case AES128CBCb:
17856
0
                    return AES128CBCb;
17857
0
            #endif
17858
0
            #ifdef WOLFSSL_AES_192
17859
0
                case AES192CBCb:
17860
0
                    return AES192CBCb;
17861
0
            #endif
17862
0
            #ifdef WOLFSSL_AES_256
17863
0
                case AES256CBCb:
17864
0
                    return AES256CBCb;
17865
0
            #endif
17866
0
            #ifndef NO_DES3
17867
0
                case DESb:
17868
0
                    return WC_NID_des;
17869
0
                case DES3b:
17870
0
                    return WC_NID_des3;
17871
0
            #endif
17872
0
            }
17873
0
            break;
17874
17875
0
    #ifdef HAVE_OCSP
17876
0
        case oidOcspType:
17877
0
            switch (oid) {
17878
0
                case OCSP_BASIC_OID:
17879
0
                    return WC_NID_id_pkix_OCSP_basic;
17880
0
                case OCSP_NONCE_OID:
17881
0
                    return OCSP_NONCE_OID;
17882
0
            }
17883
0
            break;
17884
0
    #endif /* HAVE_OCSP */
17885
17886
        /* oidCertExtType */
17887
0
        case oidCertExtType:
17888
0
            switch (oid) {
17889
0
                case BASIC_CA_OID:
17890
0
                    return WC_NID_basic_constraints;
17891
0
                case ALT_NAMES_OID:
17892
0
                    return WC_NID_subject_alt_name;
17893
0
                case CRL_DIST_OID:
17894
0
                    return WC_NID_crl_distribution_points;
17895
0
                case AUTH_INFO_OID:
17896
0
                    return WC_NID_info_access;
17897
0
                case AUTH_KEY_OID:
17898
0
                    return WC_NID_authority_key_identifier;
17899
0
                case SUBJ_KEY_OID:
17900
0
                    return WC_NID_subject_key_identifier;
17901
0
                case INHIBIT_ANY_OID:
17902
0
                    return WC_NID_inhibit_any_policy;
17903
0
                case KEY_USAGE_OID:
17904
0
                    return WC_NID_key_usage;
17905
0
                case NAME_CONS_OID:
17906
0
                    return WC_NID_name_constraints;
17907
0
                case CERT_POLICY_OID:
17908
0
                    return WC_NID_certificate_policies;
17909
0
                case EXT_KEY_USAGE_OID:
17910
0
                    return WC_NID_ext_key_usage;
17911
0
            }
17912
0
            break;
17913
17914
        /* oidCertAuthInfoType */
17915
0
        case oidCertAuthInfoType:
17916
0
            switch (oid) {
17917
0
                case AIA_OCSP_OID:
17918
0
                    return WC_NID_ad_OCSP;
17919
0
                case AIA_CA_ISSUER_OID:
17920
0
                    return WC_NID_ad_ca_issuers;
17921
0
            }
17922
0
            break;
17923
17924
        /* oidCertPolicyType */
17925
0
        case oidCertPolicyType:
17926
0
            switch (oid) {
17927
0
                case CP_ANY_OID:
17928
0
                    return WC_NID_any_policy;
17929
0
            }
17930
0
            break;
17931
17932
        /* oidCertAltNameType */
17933
0
        case oidCertAltNameType:
17934
0
            switch (oid) {
17935
0
                case HW_NAME_OID:
17936
0
                    return WC_NID_hw_name_oid;
17937
0
            }
17938
0
            break;
17939
17940
        /* oidCertKeyUseType */
17941
0
        case oidCertKeyUseType:
17942
0
            switch (oid) {
17943
0
                case EKU_ANY_OID:
17944
0
                    return WC_NID_anyExtendedKeyUsage;
17945
0
                case EKU_SERVER_AUTH_OID:
17946
0
                    return EKU_SERVER_AUTH_OID;
17947
0
                case EKU_CLIENT_AUTH_OID:
17948
0
                    return EKU_CLIENT_AUTH_OID;
17949
0
                case EKU_OCSP_SIGN_OID:
17950
0
                    return EKU_OCSP_SIGN_OID;
17951
0
            }
17952
0
            break;
17953
17954
        /* oidKdfType */
17955
0
        case oidKdfType:
17956
0
            switch (oid) {
17957
0
                case PBKDF2_OID:
17958
0
                    return PBKDF2_OID;
17959
0
            }
17960
0
            break;
17961
17962
        /* oidPBEType */
17963
0
        case oidPBEType:
17964
0
            switch (oid) {
17965
0
                case PBE_SHA1_RC4_128:
17966
0
                    return PBE_SHA1_RC4_128;
17967
0
                case PBE_SHA1_DES:
17968
0
                    return PBE_SHA1_DES;
17969
0
                case PBE_SHA1_DES3:
17970
0
                    return PBE_SHA1_DES3;
17971
0
            }
17972
0
            break;
17973
17974
        /* oidKeyWrapType */
17975
0
        case oidKeyWrapType:
17976
0
            switch (oid) {
17977
0
            #ifdef WOLFSSL_AES_128
17978
0
                case AES128_WRAP:
17979
0
                    return AES128_WRAP;
17980
0
            #endif
17981
0
            #ifdef WOLFSSL_AES_192
17982
0
                case AES192_WRAP:
17983
0
                    return AES192_WRAP;
17984
0
            #endif
17985
0
            #ifdef WOLFSSL_AES_256
17986
0
                case AES256_WRAP:
17987
0
                    return AES256_WRAP;
17988
0
            #endif
17989
0
            }
17990
0
            break;
17991
17992
        /* oidCmsKeyAgreeType */
17993
0
        case oidCmsKeyAgreeType:
17994
0
            switch (oid) {
17995
0
                #ifndef NO_SHA
17996
0
                case dhSinglePass_stdDH_sha1kdf_scheme:
17997
0
                    return dhSinglePass_stdDH_sha1kdf_scheme;
17998
0
                #endif
17999
0
                #ifdef WOLFSSL_SHA224
18000
0
                case dhSinglePass_stdDH_sha224kdf_scheme:
18001
0
                    return dhSinglePass_stdDH_sha224kdf_scheme;
18002
0
                #endif
18003
0
                #ifndef NO_SHA256
18004
0
                case dhSinglePass_stdDH_sha256kdf_scheme:
18005
0
                    return dhSinglePass_stdDH_sha256kdf_scheme;
18006
0
                #endif
18007
0
                #ifdef WOLFSSL_SHA384
18008
0
                case dhSinglePass_stdDH_sha384kdf_scheme:
18009
0
                    return dhSinglePass_stdDH_sha384kdf_scheme;
18010
0
                #endif
18011
0
                #ifdef WOLFSSL_SHA512
18012
0
                case dhSinglePass_stdDH_sha512kdf_scheme:
18013
0
                    return dhSinglePass_stdDH_sha512kdf_scheme;
18014
0
                #endif
18015
0
            }
18016
0
            break;
18017
18018
#ifdef WOLFSSL_CERT_REQ
18019
        case oidCsrAttrType:
18020
            switch (oid) {
18021
                case PKCS9_CONTENT_TYPE_OID:
18022
                    return WC_NID_pkcs9_contentType;
18023
                case CHALLENGE_PASSWORD_OID:
18024
                    return WC_NID_pkcs9_challengePassword;
18025
                case SERIAL_NUMBER_OID:
18026
                    return WC_NID_serialNumber;
18027
                case USER_ID_OID:
18028
                    return WC_NID_userId;
18029
            }
18030
            break;
18031
#endif
18032
18033
0
        default:
18034
0
            WOLFSSL_MSG("OID not in table");
18035
0
    }
18036
    /* If not found in above switch then try the table */
18037
0
    for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++) {
18038
0
        if (wolfssl_object_info[i].id == (int)oid) {
18039
0
            return wolfssl_object_info[i].nid;
18040
0
        }
18041
0
    }
18042
18043
0
    return WOLFSSL_FATAL_ERROR;
18044
0
}
18045
18046
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
18047
18048
#if defined(OPENSSL_EXTRA)
18049
18050
/* frees all nodes in the current threads error queue
18051
 *
18052
 * id  thread id. ERR_remove_state is depreciated and id is ignored. The
18053
 *     current threads queue will be free'd.
18054
 */
18055
void wolfSSL_ERR_remove_state(unsigned long id)
18056
0
{
18057
0
    WOLFSSL_ENTER("wolfSSL_ERR_remove_state");
18058
0
    (void)id;
18059
0
    if (wc_ERR_remove_state() != 0) {
18060
0
        WOLFSSL_MSG("Error with removing the state");
18061
0
    }
18062
0
}
18063
18064
#endif /* OPENSSL_EXTRA */
18065
18066
#ifdef WOLFSSL_STATIC_EPHEMERAL
18067
int wolfSSL_StaticEphemeralKeyLoad(WOLFSSL* ssl, int keyAlgo, void* keyPtr)
18068
{
18069
    int ret;
18070
    word32 idx = 0;
18071
    DerBuffer* der = NULL;
18072
18073
    if (ssl == NULL || ssl->ctx == NULL || keyPtr == NULL) {
18074
        return BAD_FUNC_ARG;
18075
    }
18076
18077
#ifndef SINGLE_THREADED
18078
    if (!ssl->ctx->staticKELockInit) {
18079
        return BUFFER_E; /* no keys set */
18080
    }
18081
    ret = wc_LockMutex(&ssl->ctx->staticKELock);
18082
    if (ret != 0) {
18083
        return ret;
18084
    }
18085
#endif
18086
18087
    ret = BUFFER_E; /* set default error */
18088
    switch (keyAlgo) {
18089
    #ifndef NO_DH
18090
        case WC_PK_TYPE_DH:
18091
            if (ssl != NULL)
18092
                der = ssl->staticKE.dhKey;
18093
            if (der == NULL)
18094
                der = ssl->ctx->staticKE.dhKey;
18095
            if (der != NULL) {
18096
                DhKey* key = (DhKey*)keyPtr;
18097
                WOLFSSL_MSG("Using static DH key");
18098
                ret = wc_DhKeyDecode(der->buffer, &idx, key, der->length);
18099
            }
18100
            break;
18101
    #endif
18102
    #ifdef HAVE_ECC
18103
        case WC_PK_TYPE_ECDH:
18104
            if (ssl != NULL)
18105
                der = ssl->staticKE.ecKey;
18106
            if (der == NULL)
18107
                der = ssl->ctx->staticKE.ecKey;
18108
            if (der != NULL) {
18109
                ecc_key* key = (ecc_key*)keyPtr;
18110
                WOLFSSL_MSG("Using static ECDH key");
18111
                ret = wc_EccPrivateKeyDecode(der->buffer, &idx, key,
18112
                    der->length);
18113
            }
18114
            break;
18115
    #endif
18116
    #ifdef HAVE_CURVE25519
18117
        case WC_PK_TYPE_CURVE25519:
18118
            if (ssl != NULL)
18119
                der = ssl->staticKE.x25519Key;
18120
            if (der == NULL)
18121
                der = ssl->ctx->staticKE.x25519Key;
18122
            if (der != NULL) {
18123
                curve25519_key* key = (curve25519_key*)keyPtr;
18124
                WOLFSSL_MSG("Using static X25519 key");
18125
18126
            #ifdef WOLFSSL_CURVE25519_BLINDING
18127
                ret = wc_curve25519_set_rng(key, ssl->rng);
18128
                if (ret == 0)
18129
            #endif
18130
                    ret = wc_Curve25519PrivateKeyDecode(der->buffer, &idx, key,
18131
                        der->length);
18132
            }
18133
            break;
18134
    #endif
18135
    #ifdef HAVE_CURVE448
18136
        case WC_PK_TYPE_CURVE448:
18137
            if (ssl != NULL)
18138
                der = ssl->staticKE.x448Key;
18139
            if (der == NULL)
18140
                der = ssl->ctx->staticKE.x448Key;
18141
            if (der != NULL) {
18142
                curve448_key* key = (curve448_key*)keyPtr;
18143
                WOLFSSL_MSG("Using static X448 key");
18144
                ret = wc_Curve448PrivateKeyDecode(der->buffer, &idx, key,
18145
                    der->length);
18146
            }
18147
            break;
18148
    #endif
18149
        default:
18150
            /* not supported */
18151
            ret = NOT_COMPILED_IN;
18152
            break;
18153
    }
18154
18155
#ifndef SINGLE_THREADED
18156
    wc_UnLockMutex(&ssl->ctx->staticKELock);
18157
#endif
18158
    return ret;
18159
}
18160
18161
static int SetStaticEphemeralKey(WOLFSSL_CTX* ctx,
18162
    StaticKeyExchangeInfo_t* staticKE, int keyAlgo, const char* key,
18163
    unsigned int keySz, int format, void* heap)
18164
{
18165
    int ret = 0;
18166
    DerBuffer* der = NULL;
18167
    byte* keyBuf = NULL;
18168
#ifndef NO_FILESYSTEM
18169
    const char* keyFile = NULL;
18170
#endif
18171
18172
    /* allow empty key to free buffer */
18173
    if (staticKE == NULL || (key == NULL && keySz > 0)) {
18174
        return BAD_FUNC_ARG;
18175
    }
18176
18177
    WOLFSSL_ENTER("SetStaticEphemeralKey");
18178
18179
    /* if just free'ing key then skip loading */
18180
    if (key != NULL) {
18181
    #ifndef NO_FILESYSTEM
18182
        /* load file from filesystem */
18183
        if (key != NULL && keySz == 0) {
18184
            size_t keyBufSz = 0;
18185
            keyFile = (const char*)key;
18186
            ret = wc_FileLoad(keyFile, &keyBuf, &keyBufSz, heap);
18187
            if (ret != 0) {
18188
                return ret;
18189
            }
18190
            keySz = (unsigned int)keyBufSz;
18191
        }
18192
        else
18193
    #endif
18194
        {
18195
            /* use as key buffer directly */
18196
            keyBuf = (byte*)key;
18197
        }
18198
18199
        if (format == WOLFSSL_FILETYPE_PEM) {
18200
        #ifdef WOLFSSL_PEM_TO_DER
18201
            int keyFormat = 0;
18202
            ret = PemToDer(keyBuf, keySz, PRIVATEKEY_TYPE, &der,
18203
                heap, NULL, &keyFormat);
18204
            /* auto detect key type */
18205
            if (ret == 0 && keyAlgo == WC_PK_TYPE_NONE) {
18206
                if (keyFormat == ECDSAk)
18207
                    keyAlgo = WC_PK_TYPE_ECDH;
18208
                else if (keyFormat == X25519k)
18209
                    keyAlgo = WC_PK_TYPE_CURVE25519;
18210
                else
18211
                    keyAlgo = WC_PK_TYPE_DH;
18212
            }
18213
        #else
18214
            ret = NOT_COMPILED_IN;
18215
        #endif
18216
        }
18217
        else {
18218
            /* Detect PK type (if required) */
18219
        #ifdef HAVE_ECC
18220
            if (keyAlgo == WC_PK_TYPE_NONE) {
18221
                word32 idx = 0;
18222
                ecc_key eccKey;
18223
                ret = wc_ecc_init_ex(&eccKey, heap, INVALID_DEVID);
18224
                if (ret == 0) {
18225
                    ret = wc_EccPrivateKeyDecode(keyBuf, &idx, &eccKey, keySz);
18226
                    if (ret == 0)
18227
                        keyAlgo = WC_PK_TYPE_ECDH;
18228
                    wc_ecc_free(&eccKey);
18229
                }
18230
            }
18231
        #endif
18232
        #if !defined(NO_DH) && defined(WOLFSSL_DH_EXTRA)
18233
            if (keyAlgo == WC_PK_TYPE_NONE) {
18234
                word32 idx = 0;
18235
                DhKey dhKey;
18236
                ret = wc_InitDhKey_ex(&dhKey, heap, INVALID_DEVID);
18237
                if (ret == 0) {
18238
                    ret = wc_DhKeyDecode(keyBuf, &idx, &dhKey, keySz);
18239
                    if (ret == 0)
18240
                        keyAlgo = WC_PK_TYPE_DH;
18241
                    wc_FreeDhKey(&dhKey);
18242
                }
18243
            }
18244
        #endif
18245
        #ifdef HAVE_CURVE25519
18246
            if (keyAlgo == WC_PK_TYPE_NONE) {
18247
                word32 idx = 0;
18248
                curve25519_key x25519Key;
18249
                ret = wc_curve25519_init_ex(&x25519Key, heap, INVALID_DEVID);
18250
                if (ret == 0) {
18251
                    ret = wc_Curve25519PrivateKeyDecode(keyBuf, &idx,
18252
                        &x25519Key, keySz);
18253
                    if (ret == 0)
18254
                        keyAlgo = WC_PK_TYPE_CURVE25519;
18255
                    wc_curve25519_free(&x25519Key);
18256
                }
18257
            }
18258
        #endif
18259
        #ifdef HAVE_CURVE448
18260
            if (keyAlgo == WC_PK_TYPE_NONE) {
18261
                word32 idx = 0;
18262
                curve448_key x448Key;
18263
                ret = wc_curve448_init(&x448Key);
18264
                if (ret == 0) {
18265
                    ret = wc_Curve448PrivateKeyDecode(keyBuf, &idx, &x448Key,
18266
                        keySz);
18267
                    if (ret == 0)
18268
                        keyAlgo = WC_PK_TYPE_CURVE448;
18269
                    wc_curve448_free(&x448Key);
18270
                }
18271
            }
18272
        #endif
18273
18274
            if (keyAlgo != WC_PK_TYPE_NONE) {
18275
                ret = AllocDer(&der, keySz, PRIVATEKEY_TYPE, heap);
18276
                if (ret == 0) {
18277
                    XMEMCPY(der->buffer, keyBuf, keySz);
18278
                }
18279
            }
18280
        }
18281
    }
18282
18283
#ifndef NO_FILESYSTEM
18284
    /* done with keyFile buffer */
18285
    if (keyFile && keyBuf) {
18286
        XFREE(keyBuf, heap, DYNAMIC_TYPE_TMP_BUFFER);
18287
    }
18288
#endif
18289
18290
#ifndef SINGLE_THREADED
18291
    if (ret == 0 && !ctx->staticKELockInit) {
18292
        ret = wc_InitMutex(&ctx->staticKELock);
18293
        if (ret == 0) {
18294
            ctx->staticKELockInit = 1;
18295
        }
18296
    }
18297
#endif
18298
    if (ret == 0
18299
    #ifndef SINGLE_THREADED
18300
        && (ret = wc_LockMutex(&ctx->staticKELock)) == 0
18301
    #endif
18302
    ) {
18303
        switch (keyAlgo) {
18304
        #ifndef NO_DH
18305
            case WC_PK_TYPE_DH:
18306
                FreeDer(&staticKE->dhKey);
18307
                staticKE->dhKey = der; der = NULL;
18308
                break;
18309
        #endif
18310
        #ifdef HAVE_ECC
18311
            case WC_PK_TYPE_ECDH:
18312
                FreeDer(&staticKE->ecKey);
18313
                staticKE->ecKey = der; der = NULL;
18314
                break;
18315
        #endif
18316
        #ifdef HAVE_CURVE25519
18317
            case WC_PK_TYPE_CURVE25519:
18318
                FreeDer(&staticKE->x25519Key);
18319
                staticKE->x25519Key = der; der = NULL;
18320
                break;
18321
        #endif
18322
        #ifdef HAVE_CURVE448
18323
            case WC_PK_TYPE_CURVE448:
18324
                FreeDer(&staticKE->x448Key);
18325
                staticKE->x448Key = der; der = NULL;
18326
                break;
18327
        #endif
18328
            default:
18329
                /* not supported */
18330
                ret = NOT_COMPILED_IN;
18331
                break;
18332
        }
18333
18334
    #ifndef SINGLE_THREADED
18335
        wc_UnLockMutex(&ctx->staticKELock);
18336
    #endif
18337
    }
18338
18339
    if (ret != 0) {
18340
        FreeDer(&der);
18341
    }
18342
18343
    (void)ctx; /* not used for single threaded */
18344
18345
    WOLFSSL_LEAVE("SetStaticEphemeralKey", ret);
18346
18347
    return ret;
18348
}
18349
18350
int wolfSSL_CTX_set_ephemeral_key(WOLFSSL_CTX* ctx, int keyAlgo,
18351
    const char* key, unsigned int keySz, int format)
18352
{
18353
    if (ctx == NULL) {
18354
        return BAD_FUNC_ARG;
18355
    }
18356
    return SetStaticEphemeralKey(ctx, &ctx->staticKE, keyAlgo,
18357
        key, keySz, format, ctx->heap);
18358
}
18359
int wolfSSL_set_ephemeral_key(WOLFSSL* ssl, int keyAlgo,
18360
    const char* key, unsigned int keySz, int format)
18361
{
18362
    if (ssl == NULL || ssl->ctx == NULL) {
18363
        return BAD_FUNC_ARG;
18364
    }
18365
    return SetStaticEphemeralKey(ssl->ctx, &ssl->staticKE, keyAlgo,
18366
        key, keySz, format, ssl->heap);
18367
}
18368
18369
static int GetStaticEphemeralKey(WOLFSSL_CTX* ctx, WOLFSSL* ssl,
18370
    int keyAlgo, const unsigned char** key, unsigned int* keySz)
18371
{
18372
    int ret = 0;
18373
    DerBuffer* der = NULL;
18374
18375
    if (key)   *key = NULL;
18376
    if (keySz) *keySz = 0;
18377
18378
#ifndef SINGLE_THREADED
18379
    if (ctx->staticKELockInit &&
18380
        (ret = wc_LockMutex(&ctx->staticKELock)) != 0) {
18381
        return ret;
18382
    }
18383
#endif
18384
18385
    switch (keyAlgo) {
18386
    #ifndef NO_DH
18387
        case WC_PK_TYPE_DH:
18388
            if (ssl != NULL)
18389
                der = ssl->staticKE.dhKey;
18390
            if (der == NULL)
18391
                der = ctx->staticKE.dhKey;
18392
            break;
18393
    #endif
18394
    #ifdef HAVE_ECC
18395
        case WC_PK_TYPE_ECDH:
18396
            if (ssl != NULL)
18397
                der = ssl->staticKE.ecKey;
18398
            if (der == NULL)
18399
                der = ctx->staticKE.ecKey;
18400
            break;
18401
    #endif
18402
    #ifdef HAVE_CURVE25519
18403
        case WC_PK_TYPE_CURVE25519:
18404
            if (ssl != NULL)
18405
                der = ssl->staticKE.x25519Key;
18406
            if (der == NULL)
18407
                der = ctx->staticKE.x25519Key;
18408
            break;
18409
    #endif
18410
    #ifdef HAVE_CURVE448
18411
        case WC_PK_TYPE_CURVE448:
18412
            if (ssl != NULL)
18413
                der = ssl->staticKE.x448Key;
18414
            if (der == NULL)
18415
                der = ctx->staticKE.x448Key;
18416
            break;
18417
    #endif
18418
        default:
18419
            /* not supported */
18420
            ret = NOT_COMPILED_IN;
18421
            break;
18422
    }
18423
18424
    if (der) {
18425
        if (key)
18426
            *key = der->buffer;
18427
        if (keySz)
18428
            *keySz = der->length;
18429
    }
18430
18431
#ifndef SINGLE_THREADED
18432
    wc_UnLockMutex(&ctx->staticKELock);
18433
#endif
18434
18435
    return ret;
18436
}
18437
18438
/* returns pointer to currently loaded static ephemeral as ASN.1 */
18439
/* this can be converted to PEM using wc_DerToPem */
18440
int wolfSSL_CTX_get_ephemeral_key(WOLFSSL_CTX* ctx, int keyAlgo,
18441
    const unsigned char** key, unsigned int* keySz)
18442
{
18443
    if (ctx == NULL) {
18444
        return BAD_FUNC_ARG;
18445
    }
18446
18447
    return GetStaticEphemeralKey(ctx, NULL, keyAlgo, key, keySz);
18448
}
18449
int wolfSSL_get_ephemeral_key(WOLFSSL* ssl, int keyAlgo,
18450
    const unsigned char** key, unsigned int* keySz)
18451
{
18452
    if (ssl == NULL || ssl->ctx == NULL) {
18453
        return BAD_FUNC_ARG;
18454
    }
18455
18456
    return GetStaticEphemeralKey(ssl->ctx, ssl, keyAlgo, key, keySz);
18457
}
18458
18459
#endif /* WOLFSSL_STATIC_EPHEMERAL */
18460
18461
#if defined(OPENSSL_EXTRA)
18462
/* wolfSSL_THREADID_current is provided as a compat API with
18463
 * CRYPTO_THREADID_current to register current thread id into given id object.
18464
 * However, CRYPTO_THREADID_current API has been deprecated and no longer
18465
 * exists in the OpenSSL 1.0.0 or later.This API only works as a stub
18466
 * like as existing wolfSSL_THREADID_set_numeric.
18467
 */
18468
void wolfSSL_THREADID_current(WOLFSSL_CRYPTO_THREADID* id)
18469
0
{
18470
0
    (void)id;
18471
0
    return;
18472
0
}
18473
/* wolfSSL_THREADID_hash is provided as a compatible API with
18474
 * CRYPTO_THREADID_hash which returns a hash value calculated from the
18475
 * specified thread id. However, CRYPTO_THREADID_hash API has been
18476
 * deprecated and no longer exists in the OpenSSL 1.0.0 or later.
18477
 * This API only works as a stub to returns 0. This behavior is
18478
 * equivalent to the latest OpenSSL CRYPTO_THREADID_hash.
18479
 */
18480
unsigned long wolfSSL_THREADID_hash(const WOLFSSL_CRYPTO_THREADID* id)
18481
0
{
18482
0
    (void)id;
18483
0
    return 0UL;
18484
0
}
18485
/* wolfSSL_set_ecdh_auto is provided as compatible API with
18486
 * SSL_set_ecdh_auto to enable auto ecdh curve selection functionality.
18487
 * Since this functionality is enabled by default in wolfSSL,
18488
 * this API exists as a stub.
18489
 */
18490
int wolfSSL_set_ecdh_auto(WOLFSSL* ssl, int onoff)
18491
0
{
18492
0
    (void)ssl;
18493
0
    (void)onoff;
18494
0
    return WOLFSSL_SUCCESS;
18495
0
}
18496
/* wolfSSL_CTX_set_ecdh_auto is provided as compatible API with
18497
 * SSL_CTX_set_ecdh_auto to enable auto ecdh curve selection functionality.
18498
 * Since this functionality is enabled by default in wolfSSL,
18499
 * this API exists as a stub.
18500
 */
18501
int wolfSSL_CTX_set_ecdh_auto(WOLFSSL_CTX* ctx, int onoff)
18502
0
{
18503
0
    (void)ctx;
18504
0
    (void)onoff;
18505
0
    return WOLFSSL_SUCCESS;
18506
0
}
18507
18508
/* wolfSSL_CTX_set_dh_auto is provided as compatible API with
18509
 * SSL_CTX_set_dh_auto to enable auto dh selection functionality.
18510
 * Since this functionality is enabled by default in wolfSSL,
18511
 * this API exists as a stub.
18512
 */
18513
int wolfSSL_CTX_set_dh_auto(WOLFSSL_CTX* ctx, int onoff)
18514
0
{
18515
0
    (void)ctx;
18516
0
    (void)onoff;
18517
0
    return WOLFSSL_SUCCESS;
18518
0
}
18519
18520
/**
18521
 * Set security level (wolfSSL doesn't support setting the security level).
18522
 *
18523
 * The security level can only be set through a system wide crypto-policy
18524
 * with wolfSSL_crypto_policy_enable().
18525
 *
18526
 * @param ctx  a pointer to WOLFSSL_CTX structure
18527
 * @param level security level
18528
 */
18529
void wolfSSL_CTX_set_security_level(WOLFSSL_CTX* ctx, int level)
18530
0
{
18531
0
    WOLFSSL_ENTER("wolfSSL_CTX_set_security_level");
18532
0
    (void)ctx;
18533
0
    (void)level;
18534
0
}
18535
18536
int wolfSSL_CTX_get_security_level(const WOLFSSL_CTX * ctx)
18537
0
{
18538
0
    WOLFSSL_ENTER("wolfSSL_CTX_get_security_level");
18539
    #if defined(WOLFSSL_SYS_CRYPTO_POLICY)
18540
    if (ctx == NULL) {
18541
        return BAD_FUNC_ARG;
18542
    }
18543
18544
    return ctx->secLevel;
18545
    #else
18546
0
    (void)ctx;
18547
0
    return 0;
18548
0
    #endif /* WOLFSSL_SYS_CRYPTO_POLICY */
18549
0
}
18550
18551
#if defined(OPENSSL_EXTRA) && defined(HAVE_SECRET_CALLBACK)
18552
/*
18553
 * This API accepts a user callback which puts key-log records into
18554
 * a KEY LOGFILE. The callback is stored into a CTX and propagated to
18555
 * each SSL object on its creation timing.
18556
 */
18557
void wolfSSL_CTX_set_keylog_callback(WOLFSSL_CTX* ctx,
18558
    wolfSSL_CTX_keylog_cb_func cb)
18559
{
18560
    WOLFSSL_ENTER("wolfSSL_CTX_set_keylog_callback");
18561
    /* stores the callback into WOLFSSL_CTX */
18562
    if (ctx != NULL) {
18563
        ctx->keyLogCb = cb;
18564
    }
18565
}
18566
wolfSSL_CTX_keylog_cb_func wolfSSL_CTX_get_keylog_callback(
18567
    const WOLFSSL_CTX* ctx)
18568
{
18569
    WOLFSSL_ENTER("wolfSSL_CTX_get_keylog_callback");
18570
    if (ctx != NULL)
18571
        return ctx->keyLogCb;
18572
    return NULL;
18573
}
18574
#endif /* OPENSSL_EXTRA && HAVE_SECRET_CALLBACK */
18575
18576
#endif /* OPENSSL_EXTRA */
18577
18578
#ifdef WOLFSSL_THREADED_CRYPT
18579
int wolfSSL_AsyncEncryptReady(WOLFSSL* ssl, int idx)
18580
{
18581
    ThreadCrypt* encrypt;
18582
18583
    if (ssl == NULL) {
18584
        return 0;
18585
    }
18586
18587
    encrypt = &ssl->buffers.encrypt[idx];
18588
    return (encrypt->avail == 0) && (encrypt->done == 0);
18589
}
18590
18591
int wolfSSL_AsyncEncryptStop(WOLFSSL* ssl, int idx)
18592
{
18593
    ThreadCrypt* encrypt;
18594
18595
    if (ssl == NULL) {
18596
        return 1;
18597
    }
18598
18599
    encrypt = &ssl->buffers.encrypt[idx];
18600
    return encrypt->stop;
18601
}
18602
18603
int wolfSSL_AsyncEncrypt(WOLFSSL* ssl, int idx)
18604
{
18605
    int ret = WC_NO_ERR_TRACE(NOT_COMPILED_IN);
18606
    ThreadCrypt* encrypt = &ssl->buffers.encrypt[idx];
18607
18608
    if (ssl->specs.bulk_cipher_algorithm == wolfssl_aes_gcm) {
18609
        unsigned char* out = encrypt->buffer.buffer + encrypt->offset;
18610
        unsigned char* input = encrypt->buffer.buffer + encrypt->offset;
18611
        word32 encSz = encrypt->buffer.length - encrypt->offset;
18612
18613
        ret =
18614
#if !defined(NO_GCM_ENCRYPT_EXTRA) && \
18615
    ((!defined(HAVE_FIPS) && !defined(HAVE_SELFTEST)) || \
18616
    (defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)))
18617
              wc_AesGcmEncrypt_ex
18618
#else
18619
              wc_AesGcmEncrypt
18620
#endif
18621
              (encrypt->encrypt.aes,
18622
               out + AESGCM_EXP_IV_SZ, input + AESGCM_EXP_IV_SZ,
18623
               encSz - AESGCM_EXP_IV_SZ - ssl->specs.aead_mac_size,
18624
               encrypt->nonce, AESGCM_NONCE_SZ,
18625
               out + encSz - ssl->specs.aead_mac_size,
18626
               ssl->specs.aead_mac_size,
18627
               encrypt->additional, AEAD_AUTH_DATA_SZ);
18628
#if !defined(NO_PUBLIC_GCM_SET_IV) && \
18629
    ((!defined(HAVE_FIPS) && !defined(HAVE_SELFTEST)) || \
18630
    (defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)))
18631
        XMEMCPY(out, encrypt->nonce + AESGCM_IMP_IV_SZ, AESGCM_EXP_IV_SZ);
18632
#endif
18633
        encrypt->done = 1;
18634
    }
18635
18636
    return ret;
18637
}
18638
18639
int wolfSSL_AsyncEncryptSetSignal(WOLFSSL* ssl, int idx,
18640
    WOLFSSL_THREAD_SIGNAL signal, void* ctx)
18641
{
18642
    int ret = 0;
18643
18644
    if (ssl == NULL) {
18645
        ret = BAD_FUNC_ARG;
18646
    }
18647
    else {
18648
        ssl->buffers.encrypt[idx].signal = signal;
18649
        ssl->buffers.encrypt[idx].signalCtx = ctx;
18650
    }
18651
18652
    return ret;
18653
}
18654
#endif
18655
18656
18657
#ifndef NO_CERT
18658
#define WOLFSSL_X509_INCLUDED
18659
#include "src/x509.c"
18660
#endif
18661
18662
/*******************************************************************************
18663
 * START OF standard C library wrapping APIs
18664
 ******************************************************************************/
18665
#if defined(OPENSSL_ALL) || (defined(OPENSSL_EXTRA) && \
18666
    (defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) || \
18667
     defined(HAVE_LIGHTY) || defined(WOLFSSL_HAPROXY) || \
18668
     defined(WOLFSSL_OPENSSH)))
18669
#ifndef NO_WOLFSSL_STUB
18670
int wolfSSL_CRYPTO_set_mem_ex_functions(void *(*m) (size_t, const char *, int),
18671
                                void *(*r) (void *, size_t, const char *,
18672
                                            int), void (*f) (void *))
18673
0
{
18674
0
    (void) m;
18675
0
    (void) r;
18676
0
    (void) f;
18677
0
    WOLFSSL_ENTER("wolfSSL_CRYPTO_set_mem_ex_functions");
18678
0
    WOLFSSL_STUB("CRYPTO_set_mem_ex_functions");
18679
18680
0
    return WOLFSSL_FAILURE;
18681
0
}
18682
#endif
18683
#endif
18684
18685
#if defined(OPENSSL_EXTRA)
18686
18687
/**
18688
 * free allocated memory resource
18689
 * @param str  a pointer to resource to be freed
18690
 * @param file dummy argument
18691
 * @param line dummy argument
18692
 */
18693
void wolfSSL_CRYPTO_free(void *str, const char *file, int line)
18694
0
{
18695
0
    (void)file;
18696
0
    (void)line;
18697
0
    XFREE(str, 0, DYNAMIC_TYPE_TMP_BUFFER);
18698
0
}
18699
/**
18700
 * allocate memory with size of num
18701
 * @param num  size of memory allocation to be malloced
18702
 * @param file dummy argument
18703
 * @param line dummy argument
18704
 * @return a pointer to allocated memory on succssesful, otherwise NULL
18705
 */
18706
void *wolfSSL_CRYPTO_malloc(size_t num, const char *file, int line)
18707
0
{
18708
0
    (void)file;
18709
0
    (void)line;
18710
0
    return XMALLOC(num, 0, DYNAMIC_TYPE_TMP_BUFFER);
18711
0
}
18712
18713
#endif
18714
18715
/*******************************************************************************
18716
 * END OF standard C library wrapping APIs
18717
 ******************************************************************************/
18718
18719
/*******************************************************************************
18720
 * START OF EX_DATA APIs
18721
 ******************************************************************************/
18722
#ifdef HAVE_EX_DATA
18723
void wolfSSL_CRYPTO_cleanup_all_ex_data(void)
18724
0
{
18725
0
    WOLFSSL_ENTER("wolfSSL_CRYPTO_cleanup_all_ex_data");
18726
0
}
18727
18728
void* wolfSSL_CRYPTO_get_ex_data(const WOLFSSL_CRYPTO_EX_DATA* ex_data, int idx)
18729
0
{
18730
0
    WOLFSSL_ENTER("wolfSSL_CRYPTO_get_ex_data");
18731
0
#ifdef MAX_EX_DATA
18732
0
    if (ex_data && idx < MAX_EX_DATA && idx >= 0) {
18733
0
        return ex_data->ex_data[idx];
18734
0
    }
18735
#else
18736
    (void)ex_data;
18737
    (void)idx;
18738
#endif
18739
0
    return NULL;
18740
0
}
18741
18742
int wolfSSL_CRYPTO_set_ex_data(WOLFSSL_CRYPTO_EX_DATA* ex_data, int idx,
18743
    void *data)
18744
0
{
18745
0
    WOLFSSL_ENTER("wolfSSL_CRYPTO_set_ex_data");
18746
0
#ifdef MAX_EX_DATA
18747
0
    if (ex_data && idx < MAX_EX_DATA && idx >= 0) {
18748
#ifdef HAVE_EX_DATA_CLEANUP_HOOKS
18749
        if (ex_data->ex_data_cleanup_routines[idx]) {
18750
            /* call cleanup then remove cleanup callback,
18751
             * since different value is being set */
18752
            if (ex_data->ex_data[idx])
18753
                ex_data->ex_data_cleanup_routines[idx](ex_data->ex_data[idx]);
18754
            ex_data->ex_data_cleanup_routines[idx] = NULL;
18755
        }
18756
#endif
18757
0
        ex_data->ex_data[idx] = data;
18758
0
        return WOLFSSL_SUCCESS;
18759
0
    }
18760
#else
18761
    (void)ex_data;
18762
    (void)idx;
18763
    (void)data;
18764
#endif
18765
0
    return WOLFSSL_FAILURE;
18766
0
}
18767
18768
#ifdef HAVE_EX_DATA_CLEANUP_HOOKS
18769
int wolfSSL_CRYPTO_set_ex_data_with_cleanup(
18770
    WOLFSSL_CRYPTO_EX_DATA* ex_data,
18771
    int idx,
18772
    void *data,
18773
    wolfSSL_ex_data_cleanup_routine_t cleanup_routine)
18774
{
18775
    WOLFSSL_ENTER("wolfSSL_CRYPTO_set_ex_data_with_cleanup");
18776
    if (ex_data && idx < MAX_EX_DATA && idx >= 0) {
18777
        if (ex_data->ex_data_cleanup_routines[idx] && ex_data->ex_data[idx])
18778
            ex_data->ex_data_cleanup_routines[idx](ex_data->ex_data[idx]);
18779
        ex_data->ex_data[idx] = data;
18780
        ex_data->ex_data_cleanup_routines[idx] = cleanup_routine;
18781
        return WOLFSSL_SUCCESS;
18782
    }
18783
    return WOLFSSL_FAILURE;
18784
}
18785
#endif /* HAVE_EX_DATA_CLEANUP_HOOKS */
18786
#endif /* HAVE_EX_DATA */
18787
18788
#ifdef HAVE_EX_DATA_CRYPTO
18789
/**
18790
 * Issues unique index for the class specified by class_index.
18791
 * Other parameter except class_index are ignored.
18792
 * Currently, following class_index are accepted:
18793
 *  - WOLF_CRYPTO_EX_INDEX_SSL
18794
 *  - WOLF_CRYPTO_EX_INDEX_SSL_CTX
18795
 *  - WOLF_CRYPTO_EX_INDEX_X509
18796
 * @param class_index index one of CRYPTO_EX_INDEX_xxx
18797
 * @param argp  parameters to be saved
18798
 * @param argl  parameters to be saved
18799
 * @param new_func a pointer to WOLFSSL_CRYPTO_EX_new
18800
 * @param dup_func a pointer to WOLFSSL_CRYPTO_EX_dup
18801
 * @param free_func a pointer to WOLFSSL_CRYPTO_EX_free
18802
 * @return index value grater or equal to zero on success, -1 on failure.
18803
 */
18804
int wolfSSL_CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
18805
                                           WOLFSSL_CRYPTO_EX_new* new_func,
18806
                                           WOLFSSL_CRYPTO_EX_dup* dup_func,
18807
                                           WOLFSSL_CRYPTO_EX_free* free_func)
18808
0
{
18809
0
    WOLFSSL_ENTER("wolfSSL_CRYPTO_get_ex_new_index");
18810
18811
0
    return wolfssl_get_ex_new_index(class_index, argl, argp, new_func,
18812
0
            dup_func, free_func);
18813
0
}
18814
#endif /* HAVE_EX_DATA_CRYPTO */
18815
18816
/*******************************************************************************
18817
 * END OF EX_DATA APIs
18818
 ******************************************************************************/
18819
18820
/*******************************************************************************
18821
 * START OF BUF_MEM API
18822
 ******************************************************************************/
18823
18824
#if defined(OPENSSL_EXTRA)
18825
18826
/* Begin functions for openssl/buffer.h */
18827
WOLFSSL_BUF_MEM* wolfSSL_BUF_MEM_new(void)
18828
0
{
18829
0
    WOLFSSL_BUF_MEM* buf;
18830
0
    buf = (WOLFSSL_BUF_MEM*)XMALLOC(sizeof(WOLFSSL_BUF_MEM), NULL,
18831
0
                                                        DYNAMIC_TYPE_OPENSSL);
18832
0
    if (buf) {
18833
0
        XMEMSET(buf, 0, sizeof(WOLFSSL_BUF_MEM));
18834
0
    }
18835
0
    return buf;
18836
0
}
18837
18838
/* non-compat API returns length of buffer on success */
18839
int wolfSSL_BUF_MEM_grow_ex(WOLFSSL_BUF_MEM* buf, size_t len,
18840
        char zeroFill)
18841
0
{
18842
18843
0
    int len_int = (int)len;
18844
0
    int mx;
18845
0
    char* tmp;
18846
18847
    /* verify provided arguments */
18848
0
    if (buf == NULL || len_int < 0) {
18849
0
        return 0; /* BAD_FUNC_ARG; */
18850
0
    }
18851
18852
    /* check to see if fits in existing length */
18853
0
    if (buf->length > len) {
18854
0
        buf->length = len;
18855
0
        return len_int;
18856
0
    }
18857
18858
    /* check to see if fits in max buffer */
18859
0
    if (buf->max >= len) {
18860
0
        if (buf->data != NULL && zeroFill) {
18861
0
            XMEMSET(&buf->data[buf->length], 0, len - buf->length);
18862
0
        }
18863
0
        buf->length = len;
18864
0
        return len_int;
18865
0
    }
18866
18867
    /* expand size, to handle growth */
18868
0
    mx = (len_int + 3) / 3 * 4;
18869
18870
#ifdef WOLFSSL_NO_REALLOC
18871
    tmp = (char*)XMALLOC(mx, NULL, DYNAMIC_TYPE_OPENSSL);
18872
    if (tmp != NULL && buf->data != NULL) {
18873
       XMEMCPY(tmp, buf->data, len_int);
18874
       XFREE(buf->data, NULL, DYNAMIC_TYPE_OPENSSL);
18875
       buf->data = NULL;
18876
    }
18877
#else
18878
    /* use realloc */
18879
0
    tmp = (char*)XREALLOC(buf->data, mx, NULL, DYNAMIC_TYPE_OPENSSL);
18880
0
#endif
18881
18882
0
    if (tmp == NULL) {
18883
0
        return 0; /* ERR_R_MALLOC_FAILURE; */
18884
0
    }
18885
0
    buf->data = tmp;
18886
18887
0
    buf->max = (size_t)mx;
18888
0
    if (zeroFill)
18889
0
        XMEMSET(&buf->data[buf->length], 0, len - buf->length);
18890
0
    buf->length = len;
18891
18892
0
    return len_int;
18893
18894
0
}
18895
18896
/* returns length of buffer on success */
18897
int wolfSSL_BUF_MEM_grow(WOLFSSL_BUF_MEM* buf, size_t len)
18898
0
{
18899
0
    return wolfSSL_BUF_MEM_grow_ex(buf, len, 1);
18900
0
}
18901
18902
/* non-compat API returns length of buffer on success */
18903
int wolfSSL_BUF_MEM_resize(WOLFSSL_BUF_MEM* buf, size_t len)
18904
0
{
18905
0
    char* tmp;
18906
0
    int mx;
18907
18908
    /* verify provided arguments */
18909
0
    if (buf == NULL || len == 0 || (int)len <= 0) {
18910
0
        return 0; /* BAD_FUNC_ARG; */
18911
0
    }
18912
18913
0
    if (len == buf->length)
18914
0
        return (int)len;
18915
18916
0
    if (len > buf->length)
18917
0
        return wolfSSL_BUF_MEM_grow_ex(buf, len, 0);
18918
18919
    /* expand size, to handle growth */
18920
0
    mx = ((int)len + 3) / 3 * 4;
18921
18922
    /* We want to shrink the internal buffer */
18923
#ifdef WOLFSSL_NO_REALLOC
18924
    tmp = (char*)XMALLOC(mx, NULL, DYNAMIC_TYPE_OPENSSL);
18925
    if (tmp != NULL && buf->data != NULL)
18926
    {
18927
        XMEMCPY(tmp, buf->data, len);
18928
        XFREE(buf->data,NULL,DYNAMIC_TYPE_OPENSSL);
18929
        buf->data = NULL;
18930
    }
18931
#else
18932
0
    tmp = (char*)XREALLOC(buf->data, mx, NULL, DYNAMIC_TYPE_OPENSSL);
18933
0
#endif
18934
18935
0
    if (tmp == NULL)
18936
0
        return 0;
18937
18938
0
    buf->data = tmp;
18939
0
    buf->length = len;
18940
0
    buf->max = (size_t)mx;
18941
18942
0
    return (int)len;
18943
0
}
18944
18945
void wolfSSL_BUF_MEM_free(WOLFSSL_BUF_MEM* buf)
18946
0
{
18947
0
    if (buf) {
18948
0
        XFREE(buf->data, NULL, DYNAMIC_TYPE_OPENSSL);
18949
0
        buf->data = NULL;
18950
0
        buf->max = 0;
18951
0
        buf->length = 0;
18952
0
        XFREE(buf, NULL, DYNAMIC_TYPE_OPENSSL);
18953
0
    }
18954
0
}
18955
/* End Functions for openssl/buffer.h */
18956
18957
#endif /* OPENSSL_EXTRA */
18958
18959
/*******************************************************************************
18960
 * END OF BUF_MEM API
18961
 ******************************************************************************/
18962
18963
#define WOLFSSL_CONF_INCLUDED
18964
#include <src/conf.c>
18965
18966
/*******************************************************************************
18967
 * START OF RAND API
18968
 ******************************************************************************/
18969
18970
#if defined(OPENSSL_EXTRA) && !defined(WOLFSSL_NO_OPENSSL_RAND_CB)
18971
static int wolfSSL_RAND_InitMutex(void)
18972
48
{
18973
#ifndef WOLFSSL_MUTEX_INITIALIZER
18974
    if (gRandMethodsInit == 0) {
18975
        if (wc_InitMutex(&gRandMethodMutex) != 0) {
18976
            WOLFSSL_MSG("Bad Init Mutex rand methods");
18977
            return BAD_MUTEX_E;
18978
        }
18979
        gRandMethodsInit = 1;
18980
    }
18981
#endif
18982
48
    return 0;
18983
48
}
18984
#endif
18985
18986
#ifdef OPENSSL_EXTRA
18987
18988
#if defined(HAVE_GETPID) && !defined(WOLFSSL_NO_GETPID) && \
18989
    ((defined(HAVE_FIPS) && FIPS_VERSION3_LE(6,0,0)) || defined(HAVE_SELFTEST))
18990
/* In older FIPS bundles add check for reseed here since it does not exist in
18991
 * the older random.c certified files. */
18992
static pid_t currentRandPid = 0;
18993
#endif
18994
18995
/* Checks if the global RNG has been created. If not then one is created.
18996
 *
18997
 * Returns WOLFSSL_SUCCESS when no error is encountered.
18998
 */
18999
int wolfSSL_RAND_Init(void)
19000
16
{
19001
16
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
19002
16
#ifdef HAVE_GLOBAL_RNG
19003
16
    if (wc_LockMutex(&globalRNGMutex) == 0) {
19004
16
        if (initGlobalRNG == 0) {
19005
16
            ret = wc_InitRng(&globalRNG);
19006
16
            if (ret == 0) {
19007
            #if defined(HAVE_GETPID) && !defined(WOLFSSL_NO_GETPID) && \
19008
                ((defined(HAVE_FIPS) && FIPS_VERSION3_LE(6,0,0)) || \
19009
                 defined(HAVE_SELFTEST))
19010
19011
                currentRandPid = getpid();
19012
            #endif
19013
16
                initGlobalRNG = 1;
19014
16
                ret = WOLFSSL_SUCCESS;
19015
16
            }
19016
16
        }
19017
0
        else {
19018
            /* GlobalRNG is already initialized */
19019
0
            ret = WOLFSSL_SUCCESS;
19020
0
        }
19021
19022
16
        wc_UnLockMutex(&globalRNGMutex);
19023
16
    }
19024
16
#endif
19025
16
    return ret;
19026
16
}
19027
19028
19029
/* WOLFSSL_SUCCESS on ok */
19030
int wolfSSL_RAND_seed(const void* seed, int len)
19031
16
{
19032
16
#ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19033
16
    if (wolfSSL_RAND_InitMutex() == 0 && wc_LockMutex(&gRandMethodMutex) == 0) {
19034
16
        if (gRandMethods && gRandMethods->seed) {
19035
0
            int ret = gRandMethods->seed(seed, len);
19036
0
            wc_UnLockMutex(&gRandMethodMutex);
19037
0
            return ret;
19038
0
        }
19039
16
        wc_UnLockMutex(&gRandMethodMutex);
19040
16
    }
19041
#else
19042
    (void)seed;
19043
    (void)len;
19044
#endif
19045
19046
    /* Make sure global shared RNG (globalRNG) is initialized */
19047
16
    return wolfSSL_RAND_Init();
19048
16
}
19049
19050
19051
/* Returns the path for reading seed data from.
19052
 * Uses the env variable $RANDFILE first if set, if not then used $HOME/.rnd
19053
 *
19054
 * Note uses stdlib by default unless XGETENV macro is overwritten
19055
 *
19056
 * fname buffer to hold path
19057
 * len   length of fname buffer
19058
 *
19059
 * Returns a pointer to fname on success and NULL on failure
19060
 */
19061
const char* wolfSSL_RAND_file_name(char* fname, unsigned long len)
19062
0
{
19063
0
#if !defined(NO_FILESYSTEM) && defined(XGETENV) && !defined(NO_GETENV)
19064
0
    char* rt;
19065
19066
0
    WOLFSSL_ENTER("wolfSSL_RAND_file_name");
19067
19068
0
    if (fname == NULL) {
19069
0
        return NULL;
19070
0
    }
19071
19072
0
    XMEMSET(fname, 0, len);
19073
19074
/* // NOLINTBEGIN(concurrency-mt-unsafe) */
19075
0
    if ((rt = XGETENV("RANDFILE")) != NULL) {
19076
0
        if (len > XSTRLEN(rt)) {
19077
0
            XMEMCPY(fname, rt, XSTRLEN(rt));
19078
0
        }
19079
0
        else {
19080
0
            WOLFSSL_MSG("RANDFILE too large for buffer");
19081
0
            rt = NULL;
19082
0
        }
19083
0
    }
19084
/* // NOLINTEND(concurrency-mt-unsafe) */
19085
19086
    /* $RANDFILE was not set or is too large, check $HOME */
19087
0
    if (rt == NULL) {
19088
0
        const char ap[] = "/.rnd";
19089
19090
0
        WOLFSSL_MSG("Environment variable RANDFILE not set");
19091
19092
/* // NOLINTBEGIN(concurrency-mt-unsafe) */
19093
0
        if ((rt = XGETENV("HOME")) == NULL) {
19094
            #ifdef XALTHOMEVARNAME
19095
            if ((rt = XGETENV(XALTHOMEVARNAME)) == NULL) {
19096
                WOLFSSL_MSG("Environment variable HOME and " XALTHOMEVARNAME
19097
                            " not set");
19098
                return NULL;
19099
            }
19100
            #else
19101
0
            WOLFSSL_MSG("Environment variable HOME not set");
19102
0
            return NULL;
19103
0
            #endif
19104
0
        }
19105
/* // NOLINTEND(concurrency-mt-unsafe) */
19106
19107
0
        if (len > XSTRLEN(rt) + XSTRLEN(ap)) {
19108
0
            fname[0] = '\0';
19109
0
            XSTRNCAT(fname, rt, len);
19110
0
            XSTRNCAT(fname, ap, len - XSTRLEN(rt));
19111
0
            return fname;
19112
0
        }
19113
0
        else {
19114
0
            WOLFSSL_MSG("Path too large for buffer");
19115
0
            return NULL;
19116
0
        }
19117
0
    }
19118
19119
0
    return fname;
19120
#else
19121
    WOLFSSL_ENTER("wolfSSL_RAND_file_name");
19122
    WOLFSSL_MSG("RAND_file_name requires filesystem and getenv support, "
19123
                "not compiled in");
19124
    (void)fname;
19125
    (void)len;
19126
    return NULL;
19127
#endif
19128
0
}
19129
19130
19131
/* Writes 1024 bytes from the RNG to the given file name.
19132
 *
19133
 * fname name of file to write to
19134
 *
19135
 * Returns the number of bytes written
19136
 */
19137
int wolfSSL_RAND_write_file(const char* fname)
19138
0
{
19139
0
    int bytes = 0;
19140
19141
0
    WOLFSSL_ENTER("wolfSSL_RAND_write_file");
19142
19143
0
    if (fname == NULL) {
19144
0
        return WOLFSSL_FAILURE;
19145
0
    }
19146
19147
0
#ifndef NO_FILESYSTEM
19148
0
    {
19149
    #ifndef WOLFSSL_SMALL_STACK
19150
        unsigned char buf[1024];
19151
    #else
19152
0
        unsigned char* buf = (unsigned char *)XMALLOC(1024, NULL,
19153
0
                                                       DYNAMIC_TYPE_TMP_BUFFER);
19154
0
        if (buf == NULL) {
19155
0
            WOLFSSL_MSG("malloc failed");
19156
0
            return WOLFSSL_FAILURE;
19157
0
        }
19158
0
    #endif
19159
0
        bytes = 1024; /* default size of buf */
19160
19161
0
        if (initGlobalRNG == 0 && wolfSSL_RAND_Init() != WOLFSSL_SUCCESS) {
19162
0
            WOLFSSL_MSG("No RNG to use");
19163
0
            WC_FREE_VAR_EX(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
19164
0
            return 0;
19165
0
        }
19166
19167
0
        if (wc_RNG_GenerateBlock(&globalRNG, buf, (word32)bytes) != 0) {
19168
0
            WOLFSSL_MSG("Error generating random buffer");
19169
0
            bytes = 0;
19170
0
        }
19171
0
        else {
19172
0
            XFILE f;
19173
19174
        #ifdef WOLFSSL_CHECK_MEM_ZERO
19175
            wc_MemZero_Add("wolfSSL_RAND_write_file buf", buf, bytes);
19176
        #endif
19177
19178
0
            f = XFOPEN(fname, "wb");
19179
0
            if (f == XBADFILE) {
19180
0
                WOLFSSL_MSG("Error opening the file");
19181
0
                bytes = 0;
19182
0
            }
19183
0
            else {
19184
0
                size_t bytes_written = XFWRITE(buf, 1, (size_t)bytes, f);
19185
0
                bytes = (int)bytes_written;
19186
0
                XFCLOSE(f);
19187
0
            }
19188
0
        }
19189
0
        ForceZero(buf, (word32)bytes);
19190
0
    #ifdef WOLFSSL_SMALL_STACK
19191
0
        XFREE(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
19192
    #elif defined(WOLFSSL_CHECK_MEM_ZERO)
19193
        wc_MemZero_Check(buf, sizeof(buf));
19194
    #endif
19195
0
    }
19196
0
#endif
19197
19198
0
    return bytes;
19199
0
}
19200
19201
#ifndef FREERTOS_TCP
19202
19203
/* These constant values are protocol values made by egd */
19204
#if defined(USE_WOLFSSL_IO) && !defined(USE_WINDOWS_API) && \
19205
    !defined(HAVE_FIPS) && defined(HAVE_HASHDRBG) && !defined(NETOS) && \
19206
    defined(HAVE_SYS_UN_H)
19207
0
    #define WOLFSSL_EGD_NBLOCK 0x01
19208
    #include <sys/un.h>
19209
#endif
19210
19211
/* This collects entropy from the path nm and seeds the global PRNG with it.
19212
 *
19213
 * nm is the file path to the egd server
19214
 *
19215
 * Returns the number of bytes read.
19216
 */
19217
int wolfSSL_RAND_egd(const char* nm)
19218
0
{
19219
0
#ifdef WOLFSSL_EGD_NBLOCK
19220
0
    struct sockaddr_un rem;
19221
0
    int fd;
19222
0
    int ret = WOLFSSL_SUCCESS;
19223
0
    word32 bytes = 0;
19224
0
    word32 idx   = 0;
19225
#ifndef WOLFSSL_SMALL_STACK
19226
    unsigned char buf[256];
19227
#else
19228
0
    unsigned char* buf;
19229
0
    buf = (unsigned char*)XMALLOC(256, NULL, DYNAMIC_TYPE_TMP_BUFFER);
19230
0
    if (buf == NULL) {
19231
0
        WOLFSSL_MSG("Not enough memory");
19232
0
        return WOLFSSL_FATAL_ERROR;
19233
0
    }
19234
0
#endif
19235
19236
0
    XMEMSET(&rem, 0, sizeof(struct sockaddr_un));
19237
0
    if (nm == NULL) {
19238
0
        WC_FREE_VAR_EX(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
19239
0
        return WOLFSSL_FATAL_ERROR;
19240
0
    }
19241
19242
0
    fd = socket(AF_UNIX, SOCK_STREAM, 0);
19243
0
    if (fd < 0) {
19244
0
        WOLFSSL_MSG("Error creating socket");
19245
0
        WC_FREE_VAR_EX(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
19246
0
        return WOLFSSL_FATAL_ERROR;
19247
0
    }
19248
0
    rem.sun_family = AF_UNIX;
19249
0
    XSTRNCPY(rem.sun_path, nm, sizeof(rem.sun_path) - 1);
19250
0
    rem.sun_path[sizeof(rem.sun_path)-1] = '\0';
19251
19252
    /* connect to egd server */
19253
0
    if (connect(fd, (struct sockaddr*)&rem, sizeof(struct sockaddr_un)) == -1) {
19254
0
        WOLFSSL_MSG("error connecting to egd server");
19255
0
        ret = WOLFSSL_FATAL_ERROR;
19256
0
    }
19257
19258
#ifdef WOLFSSL_CHECK_MEM_ZERO
19259
    if (ret == WOLFSSL_SUCCESS) {
19260
        wc_MemZero_Add("wolfSSL_RAND_egd buf", buf, 256);
19261
    }
19262
#endif
19263
0
    while (ret == WOLFSSL_SUCCESS && bytes < 255 && idx + 2 < 256) {
19264
0
        buf[idx]     = WOLFSSL_EGD_NBLOCK;
19265
0
        buf[idx + 1] = 255 - bytes; /* request 255 bytes from server */
19266
0
        ret = (int)write(fd, buf + idx, 2);
19267
0
        if (ret != 2) {
19268
0
            if (errno == EAGAIN) {
19269
0
                ret = WOLFSSL_SUCCESS;
19270
0
                continue;
19271
0
            }
19272
0
            WOLFSSL_MSG("error requesting entropy from egd server");
19273
0
            ret = WOLFSSL_FATAL_ERROR;
19274
0
            break;
19275
0
        }
19276
19277
        /* attempting to read */
19278
0
        buf[idx] = 0;
19279
0
        ret = (int)read(fd, buf + idx, 256 - bytes);
19280
0
        if (ret == 0) {
19281
0
            WOLFSSL_MSG("error reading entropy from egd server");
19282
0
            ret = WOLFSSL_FATAL_ERROR;
19283
0
            break;
19284
0
        }
19285
0
        if (ret > 0 && buf[idx] > 0) {
19286
0
            bytes += buf[idx]; /* egd stores amount sent in first byte */
19287
0
            if (bytes + idx > 255 || buf[idx] > ret) {
19288
0
                WOLFSSL_MSG("Buffer error");
19289
0
                ret = WOLFSSL_FATAL_ERROR;
19290
0
                break;
19291
0
            }
19292
0
            XMEMMOVE(buf + idx, buf + idx + 1, buf[idx]);
19293
0
            idx = bytes;
19294
0
            ret = WOLFSSL_SUCCESS;
19295
0
            if (bytes >= 255) {
19296
0
                break;
19297
0
            }
19298
0
        }
19299
0
        else {
19300
0
            if (errno == EAGAIN || errno == EINTR) {
19301
0
                WOLFSSL_MSG("EGD would read");
19302
0
                ret = WOLFSSL_SUCCESS; /* try again */
19303
0
            }
19304
0
            else if (buf[idx] == 0) {
19305
                /* if egd returned 0 then there is no more entropy to be had.
19306
                   Do not try more reads. */
19307
0
                ret = WOLFSSL_SUCCESS;
19308
0
                break;
19309
0
            }
19310
0
            else {
19311
0
                WOLFSSL_MSG("Error with read");
19312
0
                ret = WOLFSSL_FATAL_ERROR;
19313
0
            }
19314
0
        }
19315
0
    }
19316
19317
0
    if (bytes > 0 && ret == WOLFSSL_SUCCESS) {
19318
        /* call to check global RNG is created */
19319
0
        if (wolfSSL_RAND_Init() != WOLFSSL_SUCCESS) {
19320
0
            WOLFSSL_MSG("Error with initializing global RNG structure");
19321
0
            ret = WOLFSSL_FATAL_ERROR;
19322
0
        }
19323
0
        else if (wc_RNG_DRBG_Reseed(&globalRNG, (const byte*) buf, bytes)
19324
0
                != 0) {
19325
0
            WOLFSSL_MSG("Error with reseeding DRBG structure");
19326
0
            ret = WOLFSSL_FATAL_ERROR;
19327
0
        }
19328
        #ifdef SHOW_SECRETS
19329
        else { /* print out entropy found only when no error occurred */
19330
            word32 i;
19331
            printf("EGD Entropy = ");
19332
            for (i = 0; i < bytes; i++) {
19333
                printf("%02X", buf[i]);
19334
            }
19335
            printf("\n");
19336
        }
19337
        #endif
19338
0
    }
19339
19340
0
    ForceZero(buf, bytes);
19341
0
#ifdef WOLFSSL_SMALL_STACK
19342
0
    XFREE(buf, NULL, DYNAMIC_TYPE_TMP_BUFFER);
19343
#elif defined(WOLFSSL_CHECK_MEM_ZERO)
19344
    wc_MemZero_Check(buf, 256);
19345
#endif
19346
0
    close(fd);
19347
19348
0
    if (ret == WOLFSSL_SUCCESS) {
19349
0
        return (int)bytes;
19350
0
    }
19351
0
    else {
19352
0
        return ret;
19353
0
    }
19354
#else
19355
    WOLFSSL_MSG("Type of socket needed is not available");
19356
    WOLFSSL_MSG("\tor using mode where DRBG API is not available");
19357
    (void)nm;
19358
19359
    return WOLFSSL_FATAL_ERROR;
19360
#endif /* WOLFSSL_EGD_NBLOCK */
19361
0
}
19362
19363
#endif /* !FREERTOS_TCP */
19364
19365
void wolfSSL_RAND_Cleanup(void)
19366
16
{
19367
16
#ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19368
16
    if (wolfSSL_RAND_InitMutex() == 0 && wc_LockMutex(&gRandMethodMutex) == 0) {
19369
16
        if (gRandMethods && gRandMethods->cleanup)
19370
0
            gRandMethods->cleanup();
19371
16
        wc_UnLockMutex(&gRandMethodMutex);
19372
16
    }
19373
19374
    #ifndef WOLFSSL_MUTEX_INITIALIZER
19375
    if (wc_FreeMutex(&gRandMethodMutex) == 0)
19376
        gRandMethodsInit = 0;
19377
    #endif
19378
16
#endif
19379
16
#ifdef HAVE_GLOBAL_RNG
19380
16
    if (wc_LockMutex(&globalRNGMutex) == 0) {
19381
16
        if (initGlobalRNG) {
19382
16
            wc_FreeRng(&globalRNG);
19383
16
            initGlobalRNG = 0;
19384
16
        }
19385
16
        wc_UnLockMutex(&globalRNGMutex);
19386
16
    }
19387
16
#endif
19388
16
}
19389
19390
/* returns WOLFSSL_SUCCESS if the bytes generated are valid otherwise
19391
 * WOLFSSL_FAILURE */
19392
int wolfSSL_RAND_pseudo_bytes(unsigned char* buf, int num)
19393
0
{
19394
0
    int ret;
19395
0
    int hash;
19396
0
    byte secret[DRBG_SEED_LEN]; /* secret length arbitrarily chosen */
19397
19398
0
#ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19399
0
    if (wolfSSL_RAND_InitMutex() == 0 && wc_LockMutex(&gRandMethodMutex) == 0) {
19400
0
        if (gRandMethods && gRandMethods->pseudorand) {
19401
0
            ret = gRandMethods->pseudorand(buf, num);
19402
0
            wc_UnLockMutex(&gRandMethodMutex);
19403
0
            return ret;
19404
0
        }
19405
0
        wc_UnLockMutex(&gRandMethodMutex);
19406
0
    }
19407
0
#endif
19408
19409
0
#ifdef WOLFSSL_HAVE_PRF
19410
0
    #ifndef NO_SHA256
19411
0
    hash = WC_SHA256;
19412
    #elif defined(WOLFSSL_SHA384)
19413
    hash = WC_SHA384;
19414
    #elif !defined(NO_SHA)
19415
    hash = WC_SHA;
19416
    #elif !defined(NO_MD5)
19417
    hash = WC_MD5;
19418
    #endif
19419
19420
    /* get secret value from source of entropy */
19421
0
    ret = wolfSSL_RAND_bytes(secret, DRBG_SEED_LEN);
19422
19423
    /* uses input buffer to seed for pseudo random number generation, each
19424
     * thread will potentially have different results this way */
19425
0
    if (ret == WOLFSSL_SUCCESS) {
19426
0
        PRIVATE_KEY_UNLOCK();
19427
0
        ret = wc_PRF(buf, num, secret, DRBG_SEED_LEN, (const byte*)buf, num,
19428
0
                hash, NULL, INVALID_DEVID);
19429
0
        PRIVATE_KEY_LOCK();
19430
0
        ret = (ret == 0) ? WOLFSSL_SUCCESS: WOLFSSL_FAILURE;
19431
0
    }
19432
#else
19433
    /* fall back to just doing wolfSSL_RAND_bytes if PRF not avialbale */
19434
    ret = wolfSSL_RAND_bytes(buf, num);
19435
    (void)hash;
19436
    (void)secret;
19437
#endif
19438
0
    return ret;
19439
0
}
19440
19441
/* returns WOLFSSL_SUCCESS (1) if the bytes generated are valid otherwise 0
19442
 * on failure */
19443
int wolfSSL_RAND_bytes(unsigned char* buf, int num)
19444
0
{
19445
0
    int     ret = 0;
19446
0
    WC_RNG* rng = NULL;
19447
0
    WC_DECLARE_VAR(tmpRNG, WC_RNG, 1, 0);
19448
0
    int initTmpRng = 0;
19449
0
#ifdef HAVE_GLOBAL_RNG
19450
0
    int used_global = 0;
19451
0
#endif
19452
19453
0
    WOLFSSL_ENTER("wolfSSL_RAND_bytes");
19454
    /* sanity check */
19455
0
    if (buf == NULL || num < 0)
19456
        /* return code compliant with OpenSSL */
19457
0
        return 0;
19458
19459
    /* if a RAND callback has been set try and use it */
19460
0
#ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19461
0
    if (wolfSSL_RAND_InitMutex() == 0 && wc_LockMutex(&gRandMethodMutex) == 0) {
19462
0
        if (gRandMethods && gRandMethods->bytes) {
19463
0
            ret = gRandMethods->bytes(buf, num);
19464
0
            wc_UnLockMutex(&gRandMethodMutex);
19465
0
            return ret;
19466
0
        }
19467
0
        wc_UnLockMutex(&gRandMethodMutex);
19468
0
    }
19469
0
#endif
19470
0
#ifdef HAVE_GLOBAL_RNG
19471
0
    if (initGlobalRNG) {
19472
0
        if (wc_LockMutex(&globalRNGMutex) != 0) {
19473
0
            WOLFSSL_MSG("Bad Lock Mutex rng");
19474
0
            return ret;
19475
0
        }
19476
        /* the above access to initGlobalRNG is racey -- recheck it now that we
19477
         * have the lock.
19478
         */
19479
0
        if (initGlobalRNG) {
19480
        #if defined(HAVE_GETPID) && !defined(WOLFSSL_NO_GETPID) && \
19481
                ((defined(HAVE_FIPS) && FIPS_VERSION3_LE(6,0,0)) || \
19482
                 defined(HAVE_SELFTEST))
19483
            pid_t p;
19484
19485
            p = getpid();
19486
            if (p != currentRandPid) {
19487
                wc_UnLockMutex(&globalRNGMutex);
19488
                if (wolfSSL_RAND_poll() != WOLFSSL_SUCCESS) {
19489
                    WOLFSSL_MSG("Issue with check pid and reseed");
19490
                    ret = WOLFSSL_FAILURE;
19491
                }
19492
19493
                /* reclaim lock after wolfSSL_RAND_poll */
19494
                if (wc_LockMutex(&globalRNGMutex) != 0) {
19495
                    WOLFSSL_MSG("Bad Lock Mutex rng");
19496
                    return ret;
19497
                }
19498
                currentRandPid = p;
19499
            }
19500
        #endif
19501
0
            rng = &globalRNG;
19502
0
            used_global = 1;
19503
0
        }
19504
0
        else {
19505
0
            wc_UnLockMutex(&globalRNGMutex);
19506
0
        }
19507
0
    }
19508
19509
0
    if (used_global == 0)
19510
0
#endif
19511
0
    {
19512
0
        WC_ALLOC_VAR_EX(tmpRNG, WC_RNG, 1, NULL, DYNAMIC_TYPE_RNG,
19513
0
            return ret);
19514
0
        if (wc_InitRng(tmpRNG) == 0) {
19515
0
            rng = tmpRNG;
19516
0
            initTmpRng = 1;
19517
0
        }
19518
0
    }
19519
0
    if (rng) {
19520
        /* handles size greater than RNG_MAX_BLOCK_LEN */
19521
0
        int blockCount = num / RNG_MAX_BLOCK_LEN;
19522
19523
0
        while (blockCount--) {
19524
0
            ret = wc_RNG_GenerateBlock(rng, buf, RNG_MAX_BLOCK_LEN);
19525
0
            if (ret != 0) {
19526
0
                WOLFSSL_MSG("Bad wc_RNG_GenerateBlock");
19527
0
                break;
19528
0
            }
19529
0
            num -= RNG_MAX_BLOCK_LEN;
19530
0
            buf += RNG_MAX_BLOCK_LEN;
19531
0
        }
19532
19533
0
        if (ret == 0 && num)
19534
0
            ret = wc_RNG_GenerateBlock(rng, buf, (word32)num);
19535
19536
0
        if (ret != 0)
19537
0
            WOLFSSL_MSG("Bad wc_RNG_GenerateBlock");
19538
0
        else
19539
0
            ret = WOLFSSL_SUCCESS;
19540
0
    }
19541
19542
0
#ifdef HAVE_GLOBAL_RNG
19543
0
    if (used_global == 1)
19544
0
        wc_UnLockMutex(&globalRNGMutex);
19545
0
#endif
19546
0
    if (initTmpRng)
19547
0
        wc_FreeRng(tmpRNG);
19548
0
    WC_FREE_VAR_EX(tmpRNG, NULL, DYNAMIC_TYPE_RNG);
19549
19550
0
    return ret;
19551
0
}
19552
19553
19554
int wolfSSL_RAND_poll(void)
19555
0
{
19556
0
    byte  entropy[16];
19557
0
    int  ret = 0;
19558
0
    word32 entropy_sz = 16;
19559
19560
0
    WOLFSSL_ENTER("wolfSSL_RAND_poll");
19561
0
    if (initGlobalRNG == 0){
19562
0
        WOLFSSL_MSG("Global RNG no Init");
19563
0
        return  WOLFSSL_FAILURE;
19564
0
    }
19565
0
    ret = wc_GenerateSeed(&globalRNG.seed, entropy, entropy_sz);
19566
0
    if (ret != 0) {
19567
0
        WOLFSSL_MSG("Bad wc_RNG_GenerateBlock");
19568
0
        ret = WOLFSSL_FAILURE;
19569
0
    }
19570
0
    else {
19571
0
#ifdef HAVE_HASHDRBG
19572
0
        if (wc_LockMutex(&globalRNGMutex) != 0) {
19573
0
            WOLFSSL_MSG("Bad Lock Mutex rng");
19574
0
            return ret;
19575
0
        }
19576
19577
0
        ret = wc_RNG_DRBG_Reseed(&globalRNG, entropy, entropy_sz);
19578
0
        if (ret != 0) {
19579
0
            WOLFSSL_MSG("Error reseeding DRBG");
19580
0
            ret = WOLFSSL_FAILURE;
19581
0
        }
19582
0
        else {
19583
0
            ret = WOLFSSL_SUCCESS;
19584
0
        }
19585
0
        wc_UnLockMutex(&globalRNGMutex);
19586
#elif defined(HAVE_INTEL_RDRAND)
19587
        WOLFSSL_MSG("Not polling with RAND_poll, RDRAND used without "
19588
                    "HAVE_HASHDRBG");
19589
        ret = WOLFSSL_SUCCESS;
19590
#else
19591
        WOLFSSL_MSG("RAND_poll called with HAVE_HASHDRBG not set");
19592
        ret = WOLFSSL_FAILURE;
19593
#endif
19594
0
    }
19595
19596
0
    return ret;
19597
0
}
19598
19599
    /* If a valid struct is provided with function pointers, will override
19600
       RAND_seed, bytes, cleanup, add, pseudo_bytes and status.  If a NULL
19601
       pointer is passed in, it will cancel any previous function overrides.
19602
19603
       Returns WOLFSSL_SUCCESS on success, WOLFSSL_FAILURE on failure. */
19604
    int wolfSSL_RAND_set_rand_method(const WOLFSSL_RAND_METHOD *methods)
19605
0
    {
19606
0
    #ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19607
0
        if (wolfSSL_RAND_InitMutex() == 0 &&
19608
0
                wc_LockMutex(&gRandMethodMutex) == 0) {
19609
0
            gRandMethods = methods;
19610
0
            wc_UnLockMutex(&gRandMethodMutex);
19611
0
            return WOLFSSL_SUCCESS;
19612
0
        }
19613
    #else
19614
        (void)methods;
19615
    #endif
19616
0
        return WOLFSSL_FAILURE;
19617
0
    }
19618
19619
    /* Returns WOLFSSL_SUCCESS if the RNG has been seeded with enough data */
19620
    int wolfSSL_RAND_status(void)
19621
0
    {
19622
0
        int ret = WOLFSSL_SUCCESS;
19623
0
    #ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19624
0
        if (wolfSSL_RAND_InitMutex() == 0 &&
19625
0
                wc_LockMutex(&gRandMethodMutex) == 0) {
19626
0
            if (gRandMethods && gRandMethods->status)
19627
0
                ret = gRandMethods->status();
19628
0
            wc_UnLockMutex(&gRandMethodMutex);
19629
0
        }
19630
0
        else {
19631
0
            ret = WOLFSSL_FAILURE;
19632
0
        }
19633
    #else
19634
        /* wolfCrypt provides enough seed internally, so return success */
19635
    #endif
19636
0
        return ret;
19637
0
    }
19638
19639
    void wolfSSL_RAND_add(const void* add, int len, double entropy)
19640
0
    {
19641
0
    #ifndef WOLFSSL_NO_OPENSSL_RAND_CB
19642
0
        if (wolfSSL_RAND_InitMutex() == 0 &&
19643
0
                wc_LockMutex(&gRandMethodMutex) == 0) {
19644
0
            if (gRandMethods && gRandMethods->add) {
19645
                /* callback has return code, but RAND_add does not */
19646
0
                (void)gRandMethods->add(add, len, entropy);
19647
0
            }
19648
0
            wc_UnLockMutex(&gRandMethodMutex);
19649
0
        }
19650
    #else
19651
        /* wolfSSL seeds/adds internally, use explicit RNG if you want
19652
           to take control */
19653
        (void)add;
19654
        (void)len;
19655
        (void)entropy;
19656
    #endif
19657
0
    }
19658
19659
19660
#ifndef NO_WOLFSSL_STUB
19661
void wolfSSL_RAND_screen(void)
19662
0
{
19663
0
    WOLFSSL_STUB("RAND_screen");
19664
0
}
19665
#endif
19666
19667
int wolfSSL_RAND_load_file(const char* fname, long len)
19668
0
{
19669
0
    (void)fname;
19670
    /* wolfCrypt provides enough entropy internally or will report error */
19671
0
    if (len == -1)
19672
0
        return 1024;
19673
0
    else
19674
0
        return (int)len;
19675
0
}
19676
19677
#endif /* OPENSSL_EXTRA */
19678
19679
/*******************************************************************************
19680
 * END OF RAND API
19681
 ******************************************************************************/
19682
19683
/*******************************************************************************
19684
 * START OF EVP_CIPHER API
19685
 ******************************************************************************/
19686
19687
#ifdef OPENSSL_EXTRA
19688
19689
    /* store for external read of iv, WOLFSSL_SUCCESS on success */
19690
    int  wolfSSL_StoreExternalIV(WOLFSSL_EVP_CIPHER_CTX* ctx)
19691
3.48k
    {
19692
3.48k
        WOLFSSL_ENTER("wolfSSL_StoreExternalIV");
19693
19694
3.48k
        if (ctx == NULL) {
19695
0
            WOLFSSL_MSG("Bad function argument");
19696
0
            return WOLFSSL_FATAL_ERROR;
19697
0
        }
19698
19699
3.48k
        switch (ctx->cipherType) {
19700
0
#ifndef NO_AES
19701
0
#if defined(HAVE_AES_CBC) || defined(WOLFSSL_AES_DIRECT)
19702
219
            case WC_AES_128_CBC_TYPE :
19703
251
            case WC_AES_192_CBC_TYPE :
19704
325
            case WC_AES_256_CBC_TYPE :
19705
325
                WOLFSSL_MSG("AES CBC");
19706
325
                XMEMCPY(ctx->iv, &ctx->cipher.aes.reg, ctx->ivSz);
19707
325
                break;
19708
0
#endif
19709
0
#ifdef HAVE_AESGCM
19710
828
            case WC_AES_128_GCM_TYPE :
19711
965
            case WC_AES_192_GCM_TYPE :
19712
1.84k
            case WC_AES_256_GCM_TYPE :
19713
1.84k
                WOLFSSL_MSG("AES GCM");
19714
1.84k
                XMEMCPY(ctx->iv, &ctx->cipher.aes.reg, ctx->ivSz);
19715
1.84k
                break;
19716
0
#endif /* HAVE_AESGCM */
19717
0
#ifdef HAVE_AESCCM
19718
0
            case WC_AES_128_CCM_TYPE :
19719
0
            case WC_AES_192_CCM_TYPE :
19720
0
            case WC_AES_256_CCM_TYPE :
19721
0
                WOLFSSL_MSG("AES CCM");
19722
0
                XMEMCPY(ctx->iv, &ctx->cipher.aes.reg, ctx->ivSz);
19723
0
                break;
19724
0
#endif /* HAVE_AESCCM */
19725
0
#ifdef HAVE_AES_ECB
19726
0
            case WC_AES_128_ECB_TYPE :
19727
0
            case WC_AES_192_ECB_TYPE :
19728
0
            case WC_AES_256_ECB_TYPE :
19729
0
                WOLFSSL_MSG("AES ECB");
19730
0
                break;
19731
0
#endif
19732
0
#ifdef WOLFSSL_AES_COUNTER
19733
62
            case WC_AES_128_CTR_TYPE :
19734
446
            case WC_AES_192_CTR_TYPE :
19735
493
            case WC_AES_256_CTR_TYPE :
19736
493
                WOLFSSL_MSG("AES CTR");
19737
493
                XMEMCPY(ctx->iv, &ctx->cipher.aes.reg, WC_AES_BLOCK_SIZE);
19738
493
                break;
19739
0
#endif /* WOLFSSL_AES_COUNTER */
19740
0
#ifdef WOLFSSL_AES_CFB
19741
0
#if !defined(HAVE_SELFTEST) && !defined(HAVE_FIPS)
19742
0
            case WC_AES_128_CFB1_TYPE:
19743
0
            case WC_AES_192_CFB1_TYPE:
19744
0
            case WC_AES_256_CFB1_TYPE:
19745
0
                WOLFSSL_MSG("AES CFB1");
19746
0
                break;
19747
0
            case WC_AES_128_CFB8_TYPE:
19748
0
            case WC_AES_192_CFB8_TYPE:
19749
0
            case WC_AES_256_CFB8_TYPE:
19750
0
                WOLFSSL_MSG("AES CFB8");
19751
0
                break;
19752
0
#endif /* !HAVE_SELFTEST && !HAVE_FIPS */
19753
0
            case WC_AES_128_CFB128_TYPE:
19754
0
            case WC_AES_192_CFB128_TYPE:
19755
0
            case WC_AES_256_CFB128_TYPE:
19756
0
                WOLFSSL_MSG("AES CFB128");
19757
0
                break;
19758
0
#endif /* WOLFSSL_AES_CFB */
19759
0
#if defined(WOLFSSL_AES_OFB)
19760
0
            case WC_AES_128_OFB_TYPE:
19761
0
            case WC_AES_192_OFB_TYPE:
19762
0
            case WC_AES_256_OFB_TYPE:
19763
0
                WOLFSSL_MSG("AES OFB");
19764
0
                break;
19765
0
#endif /* WOLFSSL_AES_OFB */
19766
0
#ifdef WOLFSSL_AES_XTS
19767
342
            case WC_AES_128_XTS_TYPE:
19768
437
            case WC_AES_256_XTS_TYPE:
19769
437
                WOLFSSL_MSG("AES XTS");
19770
437
                break;
19771
0
#endif /* WOLFSSL_AES_XTS */
19772
0
#endif /* NO_AES */
19773
19774
#ifdef HAVE_ARIA
19775
            case WC_ARIA_128_GCM_TYPE :
19776
            case WC_ARIA_192_GCM_TYPE :
19777
            case WC_ARIA_256_GCM_TYPE :
19778
                WOLFSSL_MSG("ARIA GCM");
19779
                XMEMCPY(ctx->iv, &ctx->cipher.aria.nonce, ARIA_BLOCK_SIZE);
19780
                break;
19781
#endif /* HAVE_ARIA */
19782
19783
0
#ifndef NO_DES3
19784
226
            case WC_DES_CBC_TYPE :
19785
226
                WOLFSSL_MSG("DES CBC");
19786
226
                XMEMCPY(ctx->iv, &ctx->cipher.des.reg, DES_BLOCK_SIZE);
19787
226
                break;
19788
19789
163
            case WC_DES_EDE3_CBC_TYPE :
19790
163
                WOLFSSL_MSG("DES EDE3 CBC");
19791
163
                XMEMCPY(ctx->iv, &ctx->cipher.des3.reg, DES_BLOCK_SIZE);
19792
163
                break;
19793
0
#endif
19794
0
#ifdef WOLFSSL_DES_ECB
19795
0
            case WC_DES_ECB_TYPE :
19796
0
                WOLFSSL_MSG("DES ECB");
19797
0
                break;
19798
0
            case WC_DES_EDE3_ECB_TYPE :
19799
0
                WOLFSSL_MSG("DES3 ECB");
19800
0
                break;
19801
0
#endif
19802
0
            case WC_ARC4_TYPE :
19803
0
                WOLFSSL_MSG("ARC4");
19804
0
                break;
19805
19806
0
#if defined(HAVE_CHACHA) && defined(HAVE_POLY1305)
19807
0
            case WC_CHACHA20_POLY1305_TYPE:
19808
0
                break;
19809
0
#endif
19810
19811
0
#ifdef HAVE_CHACHA
19812
0
            case WC_CHACHA20_TYPE:
19813
0
                break;
19814
0
#endif
19815
19816
0
#ifdef WOLFSSL_SM4_ECB
19817
0
            case WC_SM4_ECB_TYPE:
19818
0
                break;
19819
0
#endif
19820
0
#ifdef WOLFSSL_SM4_CBC
19821
0
            case WC_SM4_CBC_TYPE:
19822
0
                WOLFSSL_MSG("SM4 CBC");
19823
0
                XMEMCPY(&ctx->cipher.sm4.iv, ctx->iv, SM4_BLOCK_SIZE);
19824
0
                break;
19825
0
#endif
19826
0
#ifdef WOLFSSL_SM4_CTR
19827
0
            case WC_SM4_CTR_TYPE:
19828
0
                WOLFSSL_MSG("SM4 CTR");
19829
0
                XMEMCPY(&ctx->cipher.sm4.iv, ctx->iv, SM4_BLOCK_SIZE);
19830
0
                break;
19831
0
#endif
19832
0
#ifdef WOLFSSL_SM4_GCM
19833
0
            case WC_SM4_GCM_TYPE:
19834
0
                WOLFSSL_MSG("SM4 GCM");
19835
0
                XMEMCPY(&ctx->cipher.sm4.iv, ctx->iv, SM4_BLOCK_SIZE);
19836
0
                break;
19837
0
#endif
19838
0
#ifdef WOLFSSL_SM4_CCM
19839
0
            case WC_SM4_CCM_TYPE:
19840
0
                WOLFSSL_MSG("SM4 CCM");
19841
0
                XMEMCPY(&ctx->cipher.sm4.iv, ctx->iv, SM4_BLOCK_SIZE);
19842
0
                break;
19843
0
#endif
19844
19845
0
            case WC_NULL_CIPHER_TYPE :
19846
0
                WOLFSSL_MSG("NULL");
19847
0
                break;
19848
19849
0
            default: {
19850
0
                WOLFSSL_MSG("bad type");
19851
0
                return WOLFSSL_FATAL_ERROR;
19852
342
            }
19853
3.48k
        }
19854
3.48k
        return WOLFSSL_SUCCESS;
19855
3.48k
    }
19856
19857
    /* set internal IV from external, WOLFSSL_SUCCESS on success */
19858
    int  wolfSSL_SetInternalIV(WOLFSSL_EVP_CIPHER_CTX* ctx)
19859
0
    {
19860
19861
0
        WOLFSSL_ENTER("wolfSSL_SetInternalIV");
19862
19863
0
        if (ctx == NULL) {
19864
0
            WOLFSSL_MSG("Bad function argument");
19865
0
            return WOLFSSL_FATAL_ERROR;
19866
0
        }
19867
19868
0
        switch (ctx->cipherType) {
19869
19870
0
#ifndef NO_AES
19871
0
#if defined(HAVE_AES_CBC) || defined(WOLFSSL_AES_DIRECT)
19872
0
            case WC_AES_128_CBC_TYPE :
19873
0
            case WC_AES_192_CBC_TYPE :
19874
0
            case WC_AES_256_CBC_TYPE :
19875
0
                WOLFSSL_MSG("AES CBC");
19876
0
                XMEMCPY(&ctx->cipher.aes.reg, ctx->iv, WC_AES_BLOCK_SIZE);
19877
0
                break;
19878
0
#endif
19879
0
#ifdef HAVE_AESGCM
19880
0
            case WC_AES_128_GCM_TYPE :
19881
0
            case WC_AES_192_GCM_TYPE :
19882
0
            case WC_AES_256_GCM_TYPE :
19883
0
                WOLFSSL_MSG("AES GCM");
19884
0
                XMEMCPY(&ctx->cipher.aes.reg, ctx->iv, WC_AES_BLOCK_SIZE);
19885
0
                break;
19886
0
#endif
19887
0
#ifdef HAVE_AES_ECB
19888
0
            case WC_AES_128_ECB_TYPE :
19889
0
            case WC_AES_192_ECB_TYPE :
19890
0
            case WC_AES_256_ECB_TYPE :
19891
0
                WOLFSSL_MSG("AES ECB");
19892
0
                break;
19893
0
#endif
19894
0
#ifdef WOLFSSL_AES_COUNTER
19895
0
            case WC_AES_128_CTR_TYPE :
19896
0
            case WC_AES_192_CTR_TYPE :
19897
0
            case WC_AES_256_CTR_TYPE :
19898
0
                WOLFSSL_MSG("AES CTR");
19899
0
                XMEMCPY(&ctx->cipher.aes.reg, ctx->iv, WC_AES_BLOCK_SIZE);
19900
0
                break;
19901
0
#endif
19902
19903
0
#endif /* NO_AES */
19904
19905
#ifdef HAVE_ARIA
19906
            case WC_ARIA_128_GCM_TYPE :
19907
            case WC_ARIA_192_GCM_TYPE :
19908
            case WC_ARIA_256_GCM_TYPE :
19909
                WOLFSSL_MSG("ARIA GCM");
19910
                XMEMCPY(&ctx->cipher.aria.nonce, ctx->iv, ARIA_BLOCK_SIZE);
19911
                break;
19912
#endif /* HAVE_ARIA */
19913
19914
0
#ifndef NO_DES3
19915
0
            case WC_DES_CBC_TYPE :
19916
0
                WOLFSSL_MSG("DES CBC");
19917
0
                XMEMCPY(&ctx->cipher.des.reg, ctx->iv, DES_BLOCK_SIZE);
19918
0
                break;
19919
19920
0
            case WC_DES_EDE3_CBC_TYPE :
19921
0
                WOLFSSL_MSG("DES EDE3 CBC");
19922
0
                XMEMCPY(&ctx->cipher.des3.reg, ctx->iv, DES_BLOCK_SIZE);
19923
0
                break;
19924
0
#endif
19925
0
#ifdef WOLFSSL_DES_ECB
19926
0
            case WC_DES_ECB_TYPE :
19927
0
                WOLFSSL_MSG("DES ECB");
19928
0
                break;
19929
0
            case WC_DES_EDE3_ECB_TYPE :
19930
0
                WOLFSSL_MSG("DES3 ECB");
19931
0
                break;
19932
0
#endif
19933
19934
0
            case WC_ARC4_TYPE :
19935
0
                WOLFSSL_MSG("ARC4");
19936
0
                break;
19937
19938
0
#if defined(HAVE_CHACHA) && defined(HAVE_POLY1305)
19939
0
            case WC_CHACHA20_POLY1305_TYPE:
19940
0
                break;
19941
0
#endif
19942
19943
0
#ifdef HAVE_CHACHA
19944
0
            case WC_CHACHA20_TYPE:
19945
0
                break;
19946
0
#endif
19947
19948
0
#ifdef WOLFSSL_SM4_ECB
19949
0
            case WC_SM4_ECB_TYPE:
19950
0
                break;
19951
0
#endif
19952
0
#ifdef WOLFSSL_SM4_CBC
19953
0
            case WC_SM4_CBC_TYPE:
19954
0
                WOLFSSL_MSG("SM4 CBC");
19955
0
                XMEMCPY(ctx->iv, &ctx->cipher.sm4.iv, ctx->ivSz);
19956
0
                break;
19957
0
#endif
19958
0
#ifdef WOLFSSL_SM4_CTR
19959
0
            case WC_SM4_CTR_TYPE:
19960
0
                WOLFSSL_MSG("SM4 CTR");
19961
0
                XMEMCPY(ctx->iv, &ctx->cipher.sm4.iv, ctx->ivSz);
19962
0
                break;
19963
0
#endif
19964
0
#ifdef WOLFSSL_SM4_GCM
19965
0
            case WC_SM4_GCM_TYPE:
19966
0
                WOLFSSL_MSG("SM4 GCM");
19967
0
                XMEMCPY(ctx->iv, &ctx->cipher.sm4.iv, ctx->ivSz);
19968
0
                break;
19969
0
#endif
19970
0
#ifdef WOLFSSL_SM4_CCM
19971
0
            case WC_SM4_CCM_TYPE:
19972
0
                WOLFSSL_MSG("SM4 CCM");
19973
0
                XMEMCPY(ctx->iv, &ctx->cipher.sm4.iv, ctx->ivSz);
19974
0
                break;
19975
0
#endif
19976
19977
0
            case WC_NULL_CIPHER_TYPE :
19978
0
                WOLFSSL_MSG("NULL");
19979
0
                break;
19980
19981
0
            default: {
19982
0
                WOLFSSL_MSG("bad type");
19983
0
                return WOLFSSL_FATAL_ERROR;
19984
0
            }
19985
0
        }
19986
0
        return WOLFSSL_SUCCESS;
19987
0
    }
19988
19989
#ifndef NO_DES3
19990
19991
void wolfSSL_3des_iv(WOLFSSL_EVP_CIPHER_CTX* ctx, int doset,
19992
                            unsigned char* iv, int len)
19993
0
{
19994
0
    (void)len;
19995
19996
0
    WOLFSSL_MSG("wolfSSL_3des_iv");
19997
19998
0
    if (ctx == NULL || iv == NULL) {
19999
0
        WOLFSSL_MSG("Bad function argument");
20000
0
        return;
20001
0
    }
20002
20003
0
    if (doset)
20004
0
        wc_Des3_SetIV(&ctx->cipher.des3, iv);  /* OpenSSL compat, no ret */
20005
0
    else
20006
0
        XMEMCPY(iv, &ctx->cipher.des3.reg, DES_BLOCK_SIZE);
20007
0
}
20008
20009
#endif /* NO_DES3 */
20010
20011
20012
#ifndef NO_AES
20013
20014
void wolfSSL_aes_ctr_iv(WOLFSSL_EVP_CIPHER_CTX* ctx, int doset,
20015
                      unsigned char* iv, int len)
20016
0
{
20017
0
    (void)len;
20018
20019
0
    WOLFSSL_MSG("wolfSSL_aes_ctr_iv");
20020
20021
0
    if (ctx == NULL || iv == NULL) {
20022
0
        WOLFSSL_MSG("Bad function argument");
20023
0
        return;
20024
0
    }
20025
20026
0
    if (doset)
20027
0
       (void)wc_AesSetIV(&ctx->cipher.aes, iv);  /* OpenSSL compat, no ret */
20028
0
    else
20029
0
        XMEMCPY(iv, &ctx->cipher.aes.reg, WC_AES_BLOCK_SIZE);
20030
0
}
20031
20032
#endif /* NO_AES */
20033
20034
#endif /* OPENSSL_EXTRA */
20035
20036
/*******************************************************************************
20037
 * END OF EVP_CIPHER API
20038
 ******************************************************************************/
20039
20040
#ifndef NO_CERTS
20041
20042
#define WOLFSSL_X509_STORE_INCLUDED
20043
#include <src/x509_str.c>
20044
20045
#define WOLFSSL_SSL_P7P12_INCLUDED
20046
#include <src/ssl_p7p12.c>
20047
20048
#endif /* !NO_CERTS */
20049
20050
20051
/*******************************************************************************
20052
 * BEGIN OPENSSL FIPS DRBG APIs
20053
 ******************************************************************************/
20054
#if defined(OPENSSL_EXTRA) && !defined(WC_NO_RNG) && defined(HAVE_HASHDRBG)
20055
int wolfSSL_FIPS_drbg_init(WOLFSSL_DRBG_CTX *ctx, int type, unsigned int flags)
20056
0
{
20057
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
20058
0
    if (ctx != NULL) {
20059
0
        XMEMSET(ctx, 0, sizeof(WOLFSSL_DRBG_CTX));
20060
0
        ctx->type = type;
20061
0
        ctx->xflags = (int)flags;
20062
0
        ctx->status = DRBG_STATUS_UNINITIALISED;
20063
0
        ret = WOLFSSL_SUCCESS;
20064
0
    }
20065
0
    return ret;
20066
0
}
20067
WOLFSSL_DRBG_CTX* wolfSSL_FIPS_drbg_new(int type, unsigned int flags)
20068
0
{
20069
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
20070
0
    WOLFSSL_DRBG_CTX* ctx = (WOLFSSL_DRBG_CTX*)XMALLOC(sizeof(WOLFSSL_DRBG_CTX),
20071
0
        NULL, DYNAMIC_TYPE_OPENSSL);
20072
0
    ret = wolfSSL_FIPS_drbg_init(ctx, type, flags);
20073
0
    if (ret == WOLFSSL_SUCCESS && type != 0) {
20074
0
        ret = wolfSSL_FIPS_drbg_instantiate(ctx, NULL, 0);
20075
0
    }
20076
0
    if (ret != WOLFSSL_SUCCESS) {
20077
0
        WOLFSSL_ERROR(ret);
20078
0
        wolfSSL_FIPS_drbg_free(ctx);
20079
0
        ctx = NULL;
20080
0
    }
20081
0
    return ctx;
20082
0
}
20083
int wolfSSL_FIPS_drbg_instantiate(WOLFSSL_DRBG_CTX* ctx,
20084
    const unsigned char* pers, size_t perslen)
20085
0
{
20086
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
20087
0
    if (ctx != NULL && ctx->rng == NULL) {
20088
0
    #if !defined(HAVE_SELFTEST) && (!defined(HAVE_FIPS) || \
20089
0
        (defined(HAVE_FIPS) && FIPS_VERSION_GE(5,0)))
20090
0
        ctx->rng = wc_rng_new((byte*)pers, (word32)perslen, NULL);
20091
    #else
20092
        ctx->rng = (WC_RNG*)XMALLOC(sizeof(WC_RNG), NULL, DYNAMIC_TYPE_RNG);
20093
        if (ctx->rng != NULL) {
20094
        #if defined(HAVE_FIPS) && FIPS_VERSION_GE(2,0)
20095
            ret = wc_InitRngNonce(ctx->rng, (byte*)pers, (word32)perslen);
20096
        #else
20097
            ret = wc_InitRng(ctx->rng);
20098
            (void)pers;
20099
            (void)perslen;
20100
        #endif
20101
            if (ret != 0) {
20102
                WOLFSSL_ERROR(ret);
20103
                XFREE(ctx->rng, NULL, DYNAMIC_TYPE_RNG);
20104
                ctx->rng = NULL;
20105
            }
20106
        }
20107
    #endif
20108
0
    }
20109
0
    if (ctx != NULL && ctx->rng != NULL) {
20110
0
        ctx->status = DRBG_STATUS_READY;
20111
0
        ret = WOLFSSL_SUCCESS;
20112
0
    }
20113
0
    return ret;
20114
0
}
20115
int wolfSSL_FIPS_drbg_set_callbacks(WOLFSSL_DRBG_CTX* ctx,
20116
    drbg_entropy_get entropy_get, drbg_entropy_clean entropy_clean,
20117
    size_t entropy_blocklen,
20118
    drbg_nonce_get none_get, drbg_nonce_clean nonce_clean)
20119
0
{
20120
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
20121
0
    if (ctx != NULL) {
20122
0
        ctx->entropy_get = entropy_get;
20123
0
        ctx->entropy_clean = entropy_clean;
20124
0
        ctx->entropy_blocklen = entropy_blocklen;
20125
0
        ctx->none_get = none_get;
20126
0
        ctx->nonce_clean = nonce_clean;
20127
0
        ret = WOLFSSL_SUCCESS;
20128
0
    }
20129
0
    return ret;
20130
0
}
20131
void wolfSSL_FIPS_rand_add(const void* buf, int num, double entropy)
20132
0
{
20133
    /* not implemented */
20134
0
    (void)buf;
20135
0
    (void)num;
20136
0
    (void)entropy;
20137
0
}
20138
int wolfSSL_FIPS_drbg_reseed(WOLFSSL_DRBG_CTX* ctx, const unsigned char* adin,
20139
    size_t adinlen)
20140
0
{
20141
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
20142
0
    if (ctx != NULL && ctx->rng != NULL) {
20143
0
    #if !defined(HAVE_SELFTEST) && (!defined(HAVE_FIPS) || \
20144
0
        (defined(HAVE_FIPS) && FIPS_VERSION_GE(2,0)))
20145
0
        if (wc_RNG_DRBG_Reseed(ctx->rng, adin, (word32)adinlen) == 0) {
20146
0
            ret = WOLFSSL_SUCCESS;
20147
0
        }
20148
    #else
20149
        ret = WOLFSSL_SUCCESS;
20150
        (void)adin;
20151
        (void)adinlen;
20152
    #endif
20153
0
    }
20154
0
    return ret;
20155
0
}
20156
int wolfSSL_FIPS_drbg_generate(WOLFSSL_DRBG_CTX* ctx, unsigned char* out,
20157
    size_t outlen, int prediction_resistance, const unsigned char* adin,
20158
    size_t adinlen)
20159
0
{
20160
0
    int ret = WC_NO_ERR_TRACE(WOLFSSL_FAILURE);
20161
0
    if (ctx != NULL && ctx->rng != NULL) {
20162
0
        ret = wc_RNG_GenerateBlock(ctx->rng, out, (word32)outlen);
20163
0
        if (ret == 0) {
20164
0
            ret = WOLFSSL_SUCCESS;
20165
0
        }
20166
0
    }
20167
0
    (void)prediction_resistance;
20168
0
    (void)adin;
20169
0
    (void)adinlen;
20170
0
    return ret;
20171
0
}
20172
int wolfSSL_FIPS_drbg_uninstantiate(WOLFSSL_DRBG_CTX *ctx)
20173
0
{
20174
0
    if (ctx != NULL && ctx->rng != NULL) {
20175
0
    #if !defined(HAVE_SELFTEST) && (!defined(HAVE_FIPS) || \
20176
0
        (defined(HAVE_FIPS) && FIPS_VERSION_GE(5,0)))
20177
0
        wc_rng_free(ctx->rng);
20178
    #else
20179
        wc_FreeRng(ctx->rng);
20180
        XFREE(ctx->rng, NULL, DYNAMIC_TYPE_RNG);
20181
    #endif
20182
0
        ctx->rng = NULL;
20183
0
        ctx->status = DRBG_STATUS_UNINITIALISED;
20184
0
    }
20185
0
    return WOLFSSL_SUCCESS;
20186
0
}
20187
void wolfSSL_FIPS_drbg_free(WOLFSSL_DRBG_CTX *ctx)
20188
16
{
20189
16
    if (ctx != NULL) {
20190
        /* As safety check if free'ing the default drbg, then mark global NULL.
20191
         * Technically the user should not call free on the default drbg. */
20192
0
        if (ctx == gDrbgDefCtx) {
20193
0
            gDrbgDefCtx = NULL;
20194
0
        }
20195
0
        wolfSSL_FIPS_drbg_uninstantiate(ctx);
20196
0
        XFREE(ctx, NULL, DYNAMIC_TYPE_OPENSSL);
20197
0
    }
20198
16
}
20199
WOLFSSL_DRBG_CTX* wolfSSL_FIPS_get_default_drbg(void)
20200
0
{
20201
0
    if (gDrbgDefCtx == NULL) {
20202
0
        gDrbgDefCtx = wolfSSL_FIPS_drbg_new(0, 0);
20203
0
    }
20204
0
    return gDrbgDefCtx;
20205
0
}
20206
void wolfSSL_FIPS_get_timevec(unsigned char* buf, unsigned long* pctr)
20207
0
{
20208
    /* not implemented */
20209
0
    (void)buf;
20210
0
    (void)pctr;
20211
0
}
20212
void* wolfSSL_FIPS_drbg_get_app_data(WOLFSSL_DRBG_CTX *ctx)
20213
0
{
20214
0
    if (ctx != NULL) {
20215
0
        return ctx->app_data;
20216
0
    }
20217
0
    return NULL;
20218
0
}
20219
void wolfSSL_FIPS_drbg_set_app_data(WOLFSSL_DRBG_CTX *ctx, void *app_data)
20220
0
{
20221
0
    if (ctx != NULL) {
20222
0
        ctx->app_data = app_data;
20223
0
    }
20224
0
}
20225
#endif
20226
/*******************************************************************************
20227
 * END OF OPENSSL FIPS DRBG APIs
20228
 ******************************************************************************/
20229
20230
20231
#endif /* !WOLFCRYPT_ONLY */