From 2dafd2102ca6e0481efa52cddc704b00f602dd97 Mon Sep 17 00:00:00 2001 From: cariepointer Date: Thu, 19 Sep 2019 18:11:10 -0600 Subject: [PATCH] Add Apache HTTP Server compatibility and --enable-apachehttpd option (#2466) * Added Apache httpd support `--enable-apachehttpd`. * Added `SSL_CIPHER_get_version`, `BIO_new_fp`, `SSL_SESSION_print` and `SSL_in_connect_init` compatibility API's. * Fix to expose `ASN1_UTCTIME_print` stub. * Pulled in `wolfSSL_X509_get_ext_count` from QT. * Added `X509_get_ext_count`, `BIO_set_callback`, `BIO_set_callback_arg` and `BIO_get_callback_arg`. * Added `wolfSSL_ERR_print_errors`. * Added `BIO_set_nbio` template. * Fixes for building with Apache httpd. * Added DH prime functions required for Apache httpd. * Fix and move the BN DH prime macros. * Fix for `SSL_CTX_set_tlsext_servername_arg` to have return code. * Only add the `BN_get_rfc*_prime_*` macro's if older than 1.1.0. * Added `ERR_GET_FUNC`, `SSL_CTX_clear_extra_chain_certs` prototypes. * Added `wolfSSL_CTX_set_client_cert_cb` template and `OPENSSL_load_builtin_modules` stub macro. * Added `X509_INFO` templates (`X509_INFO_new`, `X509_INFO_free`, `sk_X509_INFO_new_null`, `sk_X509_INFO_num`, `sk_X509_INFO_value`, `sk_X509_INFO_free`). Added `sk_X509_shift`. * Added BIO_set_callback, BIO_get_callback, BIO_set_callback_arg, BIO_get_callback_arg * add BIO_set_nbio, ERR_print_errors and tests * add X509 INFO stack push function * Add ASN1_UTCTIME_print and unit test * Add X509_get_ext_count unit test * initial commit of wolfSSL_PEM_X509_INFO_read_bio * Added `sk_X509_NAME_new`, `sk_X509_NAME_push`, `sk_X509_NAME_find`, `sk_X509_NAME_set_cmp_func` and `sk_X509_NAME_free`. Grouped `sk_X509_NAME_*` functions. * Cleanup sk X509 NAME/INFO pop free template. * Advance openssl compatibility to v1.1.0 for Apache httpd. Added TLS version macros. Implemented sk X509 NAME/INFO pop and pop_free. * Added `TLS_client_method` support. * Added `SSL_get_server_tmp_key` and `EC_curve_nid2nist`. * Added `SSL_CTX_set_min_proto_version` and `SSL_CTX_set_max_proto_version`. Fix for `BN_get_rfc*_prime_*` with the v1.1.0 change. * add test cases for PEM_X509_INFO_read_bio * Fixes for `BN_get_rfc*_prime_*` macros. Added template for `SSL_DH_set0_pqg`. Fix for `SSL_OP_NO_` to use Macro's (as is done in openssl). Added `SSL_set_verify_result`. Added stub for `OPENSSL_malloc_init`. * Apache httpd compatibility functions. BIO setter/getters. * implement ASN1_TIME_check and add test case * add SSL_get_client_CA_list * add initial implementation of wolfSSL_DH_set0_pqg * Add apache support to OBJ_txt2nid and unit test, add stub for OBJ_create * add X509_STORE_CTX_get1_chain, sk_free, sk_X509_dup * Add sk_SSL_COMP_num and SSL_COMP struct * implement and test of SSL_SESSION_print * add SSL_CTX_set_client_cert_cb * expand BIO_printf and add test case * Added `OCSP_CERTID_dup`. Added `ASN1_TYPE`. * add implementation for wolfSSL_get_server_tmp_key * add wolfSSL_BIO_puts and test case * Add X509_EXTENSION_get_object and X509_EXTENSION_get_data * add helper for bio flag set and null x509 stack * add test adn implementation for wolfSSL_i2d_PrivateKey * Added `ASN1_OTHERNAME`, `ACCESS_DESCRIPTION` and `GENERAL_NAME`. Added `sk_ACCESS_DESCRIPTION_pop_free` and `ACCESS_DESCRIPTION_free` stubs. * add wolfSSL_PEM_read_bio_ECPKParameters * add BIO_vfree * add X509_up_ref * add X509_STORE_CTX_set_ex_data * add _GNU_SOURCE macro and wolfSSL_EVP_read_pw_string * add wolfSSL_EVP_PKEY_ref_up function * X509_get_ext, X509V3_EXT_print, and d2i_DISPLAYTEXT stubs * add X509_set_issuer_name * add wolfSSL_sk_SSL_CIPHER_* functions and tests * add prototype for sk_X509_EXTENSION and ACCESS_DESCRIPTION * fix casting to avoid clang warning * adjust test_wolfSSL_X509_STORE_CTX test case * Added `OpenSSL_version` * renegotiate functions and additional stack functions * add aditional stub functions * Add Apache httpd requirements for ALPN, CRL, Cert Gen/Req/Ext and SecRen. Fix for `sk_X509_INFO_new_null`. * add ocsp stub functions * Proper fix for `sk_X509_INFO_new_null`. Added templates for `X509_get_ext_by_NID` and `X509_add_ext`. Added templates for `ASN1_TIME_diff` and `ASN1_TIME_set`. * x509 extension stack additions * Fixed template for `OCSP_id_get0_info`. * add X509 stub functions * add X509_STORE_CTX_get0_store() and unit test * Added `EVP_PKEY_CTX_new_id`, `EVP_PKEY_CTX_set_rsa_keygen_bits`, `EVP_PKEY_keygen_init`, `EVP_PKEY_keygen` and `BN_to_ASN1_INTEGER`. * x509v3 stubs and req add extensions * Add OBJ_txt2obj and unit test; add long name to wolfssl_object_info table for use by OBJ_* functions * wolfSSL_set_alpn_protos implementation * Added `EVP_SignInit_ex` and `TLS_server_method` implementation. Added stubs for `RSA_get0_key` and `i2d_OCSP_REQUEST_bio`. Fix typo on `OCSP_response_create`. Fix warning in `wolfSSL_set_alpn_protos`. * Added `X509_EXTENSION_free` stub. Fixed a few macro typos/adding missing. * add X509_STORE_CTX_get0_current_issuer and unit test * add OBJ_cmp and unit test * add RSA_get0_key and unit test * add OCSP_check_nonce * Implement X509_set_notAfter/notBefore/serialNumber/version,X509_STORE_CTX_set_depth,X509V3_set_ctx. * Modify wolfSSL_X509_set_notAfter/notBefore and add tests for each. * Add test_wolfSSL_X509_set_version w/ fixes to _set_version and fix _set_notBefore/notAfter tests * add OCSP_id_get0_info and unit test, move WOLFSSL_ASN1_INTEGER to asn_public.h from ssl.h * inital implementation of wolfSSL_X509_sign * add debugging messages and set data for BIO's * Add i2d_OCSP_REQUEST_bio. * implementation of some WOLFSSL_BIO_METHOD custom functions * fix for ASN time structure and remove log node * initial eNULL support and sanity checks * fixes after rebasing code * adjust test cases and ASN1_TIME print * Various fixes for memory leaks * Apache compatibility in CTX_set_client_CA_list for X509_NAME use; add X509_NAME_dup as supporting function * Add initial X509_STORE_load_locations stub for Apache * Updates to X509_get_ext_d2i to return GENERAL_NAME struct instead of ASN1_OBJECT for alternative names and add supporting GENERAL_NAME functions * Add X509_STORE_load_locations implementation; add wolfSSL_CertManagerLoadCRL_ex; initial renegotiation fixes/updates * Fix for freeing peer cert in wolfSSL_Rehandshake instead of FreeHandShakeResources during secure renegotiation * Add X509_ALGOR and X509_PUBKEY structs for X509_PUBKEY_get0_param and X509_get_X509_PUBKEY implementation * Initial implementation of wolfSSL_X509_get_X509_PUBKEY and wolfSSL_X509_PUBKEY_get0_param * Add implementation for X509_get0_tbs_sigalg and X509_ALGOR_get0 * Add OBJ_nid2ln implementation * Fix compile errors in tests/api.c for some build options * Updates to X509_STORE_load_locations for non-CRL types; Add additional DETECT_CERT_TYPE enum and logic for detecting certificate type in ProcessFile * Add X509_STORE_load_locations unit test and minor error handling fixes * Add unit test for X509_sign * Set correct alert type for revoked certificates; add/fix a few WOLFSSL_ENTER messages * Add X509_ALGOR member to X509 struct; refactoring and unit tests for wolfSSL_X509_ALGOR_get0 and wolfSSL_X509_get0_tbs_sigalg * Add X509_PUBKEY member to X509 struct; refactoring and unit tests for wolfSSL_X509_get_X509_PUBKEY and wolfSSL_X509_PUBKEY_get0_param * Stack fixes after rebase * Secure renegotiation refactoring: add ACCEPT_BEGIN_RENEG to AcceptState for use in wolfSSL_SSL_in_connect_init; free old peer cert when receiving new cert to fix memory leak * Move enc-then-mac enable option in configure.ac for apache httpd compatibility * Simplify wolfSSL_SSL_in_connect_init logic * Remove unneeded wolfSSL_CertManagerLoadCRL_ex * Fixes for jenkins test failures * SSL_get_secure_renegotiation_support for print statement in Apache --- configure.ac | 113 +- examples/client/client.c | 15 + src/bio.c | 335 ++- src/internal.c | 151 +- src/ocsp.c | 202 +- src/ssl.c | 4480 +++++++++++++++++++++++++++----- src/tls.c | 61 + src/tls13.c | 3 + src/wolfio.c | 25 +- tests/api.c | 1155 +++++++- wolfcrypt/src/asn.c | 45 +- wolfcrypt/src/evp.c | 248 +- wolfcrypt/src/logging.c | 22 +- wolfssl/error-ssl.h | 1 + wolfssl/internal.h | 60 +- wolfssl/ocsp.h | 27 +- wolfssl/openssl/asn1.h | 18 +- wolfssl/openssl/bio.h | 58 +- wolfssl/openssl/bn.h | 13 + wolfssl/openssl/crypto.h | 3 +- wolfssl/openssl/dh.h | 16 +- wolfssl/openssl/ec.h | 3 + wolfssl/openssl/evp.h | 22 + wolfssl/openssl/include.am | 1 + wolfssl/openssl/objects.h | 10 + wolfssl/openssl/ocsp.h | 17 + wolfssl/openssl/opensslv.h | 7 +- wolfssl/openssl/pem.h | 6 + wolfssl/openssl/rsa.h | 7 +- wolfssl/openssl/ssl.h | 142 +- wolfssl/openssl/x509.h | 3 + wolfssl/openssl/x509_vfy.h | 1 + wolfssl/openssl/x509v3.h | 22 +- wolfssl/ssl.h | 431 ++- wolfssl/wolfcrypt/asn.h | 31 +- wolfssl/wolfcrypt/asn_public.h | 21 +- wolfssl/wolfcrypt/logging.h | 5 +- wolfssl/wolfcrypt/memory.h | 2 +- wolfssl/wolfcrypt/wc_port.h | 2 +- wolfssl/wolfio.h | 1 + 40 files changed, 6929 insertions(+), 856 deletions(-) create mode 100644 wolfssl/openssl/x509_vfy.h diff --git a/configure.ac b/configure.ac index 0a4312222..0a7eeddb6 100644 --- a/configure.ac +++ b/configure.ac @@ -2941,19 +2941,6 @@ then AM_CFLAGS="$AM_CFLAGS -DHAVE_EXTENDED_MASTER" fi -# Encrypt-Then-Mac -AC_ARG_ENABLE([enc-then-mac], - [AS_HELP_STRING([--enable-enc-then-mac],[Enable Encryptr-Then-Mac extension (default: enabled)])], - [ ENABLED_ENCRYPT_THEN_MAC=$enableval ], - [ ENABLED_ENCRYPT_THEN_MAC=yes ] - ) - -if test "x$ENABLED_ENCRYPT_THEN_MAC" = "xyes" -then - AM_CFLAGS="$AM_CFLAGS -DHAVE_ENCRYPT_THEN_MAC" -fi - - # TLS Extensions AC_ARG_ENABLE([tlsx], [AS_HELP_STRING([--enable-tlsx],[Enable all TLS Extensions (default: disabled)])], @@ -2974,7 +2961,7 @@ then ENABLED_ALPN=yes ENABLED_TRUSTED_CA=yes ENABLED_ENCRYPT_THEN_MAC=yes - AM_CFLAGS="$AM_CFLAGS -DHAVE_TLS_EXTENSIONS -DHAVE_SNI -DHAVE_MAX_FRAGMENT -DHAVE_TRUNCATED_HMAC -DHAVE_ALPN -DHAVE_TRUSTED_CA -DHAVE_ENCRYPT_THEN_MAC" + AM_CFLAGS="$AM_CFLAGS -DHAVE_TLS_EXTENSIONS -DHAVE_SNI -DHAVE_MAX_FRAGMENT -DHAVE_TRUNCATED_HMAC -DHAVE_ALPN -DHAVE_TRUSTED_CA" # Check the ECC supported curves prereq AS_IF([test "x$ENABLED_ECC" = "xyes" || test "x$ENABLED_CURVE25519" = "xyes"], [ENABLED_SUPPORTED_CURVES=yes @@ -3348,6 +3335,103 @@ then fi fi +# Apache HTTPD +AC_ARG_ENABLE([apachehttpd], + [AS_HELP_STRING([--enable-apachehttpd],[Enable Apache httpd (default: disabled)])], + [ ENABLED_APACHE_HTTPD=$enableval ], + [ ENABLED_APACHE_HTTPD=no ] + ) +if test "$ENABLED_APACHE_HTTPD" = "yes" +then + # Requires opensslextra and opensslall + if test "x$ENABLED_OPENSSLALL" = "xno" && test "x$ENABLED_OPENSSLCOEXIST" = "xno" + then + ENABLED_OPENSSLALL="yes" + ENABLED_OPENSSLEXTRA="yes" + AM_CFLAGS="-DOPENSSL_EXTRA -DOPENSSL_ALL $AM_CFLAGS" + fi + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_APACHE_HTTPD" + AM_CFLAGS="$AM_CFLAGS -DOPENSSL_NO_SSL2 -DOPENSSL_NO_SSL3 -DOPENSSL_NO_COMP" + AM_CFLAGS="$AM_CFLAGS -DHAVE_EX_DATA -DWOLFSSL_SIGNER_DER_CERT" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_CERT_EXT -DWOLFSSL_CERT_GEN" + + # Requires OCSP make sure on + if test "x$ENABLED_OCSP" = "xno" + then + ENABLED_OCSP="yes" + AM_CFLAGS="$AM_CFLAGS -DHAVE_OCSP" + AM_CONDITIONAL([BUILD_OCSP], [test "x$ENABLED_OCSP" = "xyes"]) + fi + + # Requires sessioncerts make sure on + if test "x$ENABLED_SESSIONCERTS" = "xno" + then + ENABLED_SESSIONCERTS="yes" + AM_CFLAGS="$AM_CFLAGS -DSESSION_CERTS" + fi + + # Requires ALPN + if test "x$ENABLED_ALPN" = "xno" + then + ENABLED_ALPN="yes" + AM_CFLAGS="$AM_CFLAGS -DHAVE_TLS_EXTENSIONS -DHAVE_ALPN" + fi + + # Requires CRL + if test "x$ENABLED_CRL" = "xno" + then + ENABLED_CRL="yes" + AM_CFLAGS="$AM_CFLAGS -DHAVE_CRL" + AM_CONDITIONAL([BUILD_CRL], [test "x$ENABLED_CRL" = "xyes"]) + fi + + # Requires Certificate Generation, Request and Extensions + if test "x$ENABLED_CERTGEN" = "xno" + then + ENABLED_CERTGEN="yes" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_CERT_GEN" + fi + if test "x$ENABLED_CERTREQ" = "xno" + then + ENABLED_CERTREQ="yes" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_CERT_REQ" + fi + if test "x$ENABLED_CERTEXT" = "xno" + then + ENABLED_CERTEXT="yes" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_CERT_EXT" + fi + + # Requires Secure Renegotiation + if test "x$ENABLED_SECURE_RENEGOTIATION" = "xno" + then + AM_CFLAGS="$AM_CFLAGS -DHAVE_SECURE_RENEGOTIATION -DHAVE_SERVER_RENEGOTIATION_INFO" + fi +fi + +# Encrypt-Then-Mac +AC_ARG_ENABLE([enc-then-mac], + [AS_HELP_STRING([--enable-enc-then-mac],[Enable Encryptr-Then-Mac extension (default: enabled)])], + [ ENABLED_ENCRYPT_THEN_MAC=$enableval ], + [ ENABLED_ENCRYPT_THEN_MAC=yes ] + ) + +if test "x$ENABLED_APACHE_HTTPD" = "xyes" +then + ENABLED_ENCRYPT_THEN_MAC=no +fi + +if test "x$ENABLED_TLSX" = "xyes" +then + ENABLED_ENCRYPT_THEN_MAC=yes +fi + +if test "x$ENABLED_ENCRYPT_THEN_MAC" = "xyes" +then + AM_CFLAGS="$AM_CFLAGS -DHAVE_ENCRYPT_THEN_MAC" +fi + + # stunnel Support AC_ARG_ENABLE([stunnel], [AS_HELP_STRING([--enable-stunnel],[Enable stunnel (default: disabled)])], @@ -5011,6 +5095,7 @@ echo " * I/O POOL: $ENABLED_IOPOOL" echo " * LIGHTY: $ENABLED_LIGHTY" echo " * HAPROXY: $ENABLED_HAPROXY" echo " * STUNNEL: $ENABLED_STUNNEL" +echo " * Apache httpd: $ENABLED_APACHE_HTTPD" echo " * NGINX: $ENABLED_NGINX" echo " * ASIO: $ENABLED_ASIO" echo " * SIGNAL: $ENABLED_SIGNAL" diff --git a/examples/client/client.c b/examples/client/client.c index 75e1ae262..3f2931ee2 100644 --- a/examples/client/client.c +++ b/examples/client/client.c @@ -2874,7 +2874,22 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) for (pt = rnd; pt < rnd + size; pt++) printf("%02X", *pt); printf("\n"); XFREE(rnd, NULL, DYNAMIC_TYPE_TMP_BUFFER); + } + + #if defined(OPENSSL_ALL) + /* print out session to stdout */ + { + WOLFSSL_BIO* bio = wolfSSL_BIO_new_fp(stdout, BIO_NOCLOSE); + if (bio != NULL) { + if (wolfSSL_SESSION_print(bio, wolfSSL_get_session(ssl)) != + WOLFSSL_SUCCESS) { + wolfSSL_BIO_printf(bio, "ERROR: Unable to print out session\n"); + } + } + wolfSSL_BIO_free(bio); + } + #endif #endif if (doSTARTTLS) { diff --git a/src/bio.c b/src/bio.c index c4b225759..471c5eadf 100644 --- a/src/bio.c +++ b/src/bio.c @@ -169,12 +169,26 @@ int wolfSSL_BIO_read(WOLFSSL_BIO* bio, void* buf, int len) WOLFSSL_ENTER("wolfSSL_BIO_read"); + /* info cb, abort if user returns <= 0*/ + if (front != NULL && front->infoCb != NULL) { + ret = (int)front->infoCb(front, WOLFSSL_BIO_CB_READ, (const char*)buf, + len, 0, 1); + if (ret <= 0) { + return ret; + } + } + /* start at end of list and work backwards */ while ((bio != NULL) && (bio->next != NULL)) { bio = bio->next; } while (bio != NULL && ret >= 0) { + /* check for custom read */ + if (bio && bio->method->custom && bio->method->custom->readCb) { + ret = bio->method->custom->readCb(bio, (char*)buf, len); + } + /* formating data */ if (bio->type == WOLFSSL_BIO_BASE64 && ret > 0 && sz > 0) { ret = wolfSSL_BIO_BASE64_read(bio, buf, sz); @@ -212,6 +226,13 @@ int wolfSSL_BIO_read(WOLFSSL_BIO* bio, void* buf, int len) bio = bio->prev; } + /* info cb, user can override return value */ + if (front != NULL && front->infoCb != NULL) { + ret = (int)front->infoCb(front, + WOLFSSL_BIO_CB_READ | WOLFSSL_BIO_CB_RETURN, + (const char*)buf, len, 0, ret); + } + return ret; } @@ -410,7 +431,21 @@ int wolfSSL_BIO_write(WOLFSSL_BIO* bio, const void* data, int len) WOLFSSL_ENTER("wolfSSL_BIO_write"); + /* info cb, abort if user returns <= 0*/ + if (front != NULL && front->infoCb != NULL) { + ret = (int)front->infoCb(front, WOLFSSL_BIO_CB_WRITE, + (const char*)data, len, 0, 1); + if (ret <= 0) { + return ret; + } + } + while (bio != NULL && ret >= 0) { + /* check for custom write */ + if (bio && bio->method->custom && bio->method->custom->writeCb) { + ret = bio->method->custom->writeCb(bio, (const char*)data, len); + } + /* check for formating */ if (bio && bio->type == WOLFSSL_BIO_BASE64) { #if defined(WOLFSSL_BASE64_ENCODE) @@ -497,10 +532,18 @@ int wolfSSL_BIO_write(WOLFSSL_BIO* bio, const void* data, int len) XFREE(frmt, front->heap, DYNAMIC_TYPE_TMP_BUFFER); } + /* info cb, user can override return value */ + if (front != NULL && front->infoCb != NULL) { + ret = (int)front->infoCb(front, + WOLFSSL_BIO_CB_WRITE | WOLFSSL_BIO_CB_RETURN, + (const char*)data, 0, 0, ret); + } + return ret; } +/* NOTE: add support for bio->infoCb() when implemented */ WOLFSSL_API long wolfSSL_BIO_ctrl(WOLFSSL_BIO *bio, int cmd, long larg, void *parg) { (void)bio; @@ -508,6 +551,11 @@ WOLFSSL_API long wolfSSL_BIO_ctrl(WOLFSSL_BIO *bio, int cmd, long larg, void *pa (void)larg; (void)parg; + if (bio && bio->method && bio->method->custom && + bio->method->custom->ctrlCb) { + return bio->method->custom->ctrlCb(bio, cmd, larg, parg); + } + WOLFSSL_STUB("BIO_ctrl"); return 0; } @@ -556,6 +604,19 @@ int wolfSSL_BIO_gets(WOLFSSL_BIO* bio, char* buf, int sz) return 0; } + /* info cb, abort if user returns <= 0*/ + if (bio->infoCb != NULL) { + ret = (int)bio->infoCb(bio, WOLFSSL_BIO_CB_GETS, buf, sz, 0, 1); + if (ret <= 0) { + return ret; + } + } + + /* check if is custom method */ + if (bio->method->custom && bio->method->custom->getsCb) { + return bio->method->custom->getsCb(bio, buf, sz); + } + switch (bio->type) { #ifndef NO_FILESYSTEM case WOLFSSL_BIO_FILE: @@ -644,10 +705,47 @@ int wolfSSL_BIO_gets(WOLFSSL_BIO* bio, char* buf, int sz) WOLFSSL_MSG("BIO type not supported yet with wolfSSL_BIO_gets"); } + /* info cb, user can override return value */ + if (bio->infoCb != NULL) { + ret = (int)bio->infoCb(bio, WOLFSSL_BIO_CB_GETS | WOLFSSL_BIO_CB_RETURN, + buf, sz, 0, ret); + } + return ret; } +/* Writes a null terminated string to bio. + * + * bio the structure to write to + * buf buffer to holding input string + * + * returns the size of the result placed in bio on success and a 0 or negative + * value in an error case. -2 is returned if the implementation is not + * supported for the BIO type. + */ +int wolfSSL_BIO_puts(WOLFSSL_BIO* bio, const char* buf) +{ + int sz; + + if (bio == NULL || buf == NULL) { + return WOLFSSL_FATAL_ERROR; + } + + /* check if is custom method */ + if (bio->method->custom && bio->method->custom->putsCb) { + return bio->method->custom->putsCb(bio, buf); + } + + sz = (int)XSTRLEN(buf); + if (sz <= 0) { + return WOLFSSL_FATAL_ERROR; + } + + return wolfSSL_BIO_write(bio, buf, sz); +} + + /* searches through bio list for a BIO of type "type" * returns NULL on failure to find a given type */ WOLFSSL_BIO* wolfSSL_BIO_find_type(WOLFSSL_BIO* bio, int type) @@ -718,7 +816,7 @@ size_t wolfSSL_BIO_wpending(const WOLFSSL_BIO *bio) /* Return the number of pending bytes in read and write buffers */ size_t wolfSSL_BIO_ctrl_pending(WOLFSSL_BIO *bio) { - WOLFSSL_ENTER("BIO_ctrl_pending"); + WOLFSSL_ENTER("wolfSSL_BIO_ctrl_pending"); if (bio == NULL) { return 0; } @@ -1159,5 +1257,240 @@ long wolfSSL_BIO_set_mem_eof_return(WOLFSSL_BIO *bio, int v) return 0; } + + +void wolfSSL_BIO_set_callback(WOLFSSL_BIO *bio, wolf_bio_info_cb callback_func) +{ + WOLFSSL_ENTER("wolfSSL_BIO_set_callback"); + + if (bio != NULL) { + bio->infoCb = callback_func; + } +} + + +wolf_bio_info_cb wolfSSL_BIO_get_callback(WOLFSSL_BIO *bio) +{ + WOLFSSL_ENTER("wolfSSL_BIO_get_callback"); + + if (bio != NULL) { + return bio->infoCb; + } + + return NULL; +} + + +void wolfSSL_BIO_set_callback_arg(WOLFSSL_BIO *bio, char *arg) +{ + WOLFSSL_ENTER("wolfSSL_BIO_set_callback_arg"); + + if (bio != NULL) { + bio->infoArg = arg; + } +} + + +char* wolfSSL_BIO_get_callback_arg(const WOLFSSL_BIO *bio) +{ + WOLFSSL_ENTER("wolfSSL_BIO_get_callback_arg"); + + if (bio != NULL) { + return bio->infoArg; + } + + return NULL; +} + + +/* store a user pointer in the WOLFSSL_BIO structure */ +void wolfSSL_BIO_set_data(WOLFSSL_BIO* bio, void *ptr) +{ + WOLFSSL_ENTER("wolfSSL_BIO_set_data"); + + if (bio != NULL) { + bio->usrCtx = ptr; + } +} + + +void* wolfSSL_BIO_get_data(WOLFSSL_BIO* bio) +{ + WOLFSSL_ENTER("wolfSSL_BIO_get_data"); + + if (bio != NULL) + return bio->usrCtx; + + WOLFSSL_MSG("WOLFSSL_BIO was null"); + return NULL; +} + +/* If flag is 0 then blocking is set, if 1 then non blocking. + * Always returns 1 + */ +long wolfSSL_BIO_set_nbio(WOLFSSL_BIO* bio, long on) +{ + #ifndef WOLFSSL_DTLS + (void)on; + #endif + WOLFSSL_ENTER("wolfSSL_BIO_set_nbio"); + + switch (bio->type) { + case WOLFSSL_BIO_SOCKET: + #ifdef XFCNTL + { + int flag = XFCNTL(bio->fd, F_GETFL, 0); + if (on) + XFCNTL(bio->fd, F_SETFL, flag | O_NONBLOCK); + else + XFCNTL(bio->fd, F_SETFL, flag & ~O_NONBLOCK); + } + #endif + break; + case WOLFSSL_BIO_SSL: + #ifdef WOLFSSL_DTLS + wolfSSL_dtls_set_using_nonblock(bio->ssl, (int)on); + #endif + break; + + default: + WOLFSSL_MSG("Unsupported bio type for non blocking"); + break; + } + + return 1; +} + + + +/* creates a new custom WOLFSSL_BIO_METHOD */ +WOLFSSL_BIO_METHOD *wolfSSL_BIO_meth_new(int type, const char *name) +{ + WOLFSSL_BIO_METHOD* meth; + WOLFSSL_BIO_METHOD_CUSTOM* custom; + + WOLFSSL_ENTER("wolfSSL_BIO_meth_new"); + + meth = (WOLFSSL_BIO_METHOD*)XMALLOC(sizeof(WOLFSSL_BIO_METHOD), NULL, + DYNAMIC_TYPE_OPENSSL); + if (meth == NULL) { + WOLFSSL_MSG("Error allocating memory for WOLFSSL_BIO_METHOD"); + return NULL; + } + XMEMSET(meth, 0, sizeof(WOLFSSL_BIO_METHOD)); + meth->type = (byte)type; + + custom = (WOLFSSL_BIO_METHOD_CUSTOM*)XMALLOC( + sizeof(WOLFSSL_BIO_METHOD_CUSTOM), NULL, DYNAMIC_TYPE_OPENSSL); + if (custom == NULL) { + WOLFSSL_MSG("Error allocating memory for WOLFSSL_BIO_METHOD_CUSTOM"); + wolfSSL_BIO_meth_free(meth); + return NULL; + } + + XMEMSET(custom, 0, sizeof(WOLFSSL_BIO_METHOD_CUSTOM)); + meth->custom = custom; + + XSTRNCPY(custom->name, name, MAX_BIO_METHOD_NAME - 1); + return meth; +} + + +void wolfSSL_BIO_meth_free(WOLFSSL_BIO_METHOD *biom) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_free"); + if (biom) { + if (biom->custom) { + XFREE(biom->custom, NULL, DYNAMIC_TYPE_OPENSSL); + } + XFREE(biom, NULL, DYNAMIC_TYPE_OPENSSL); + } +} + + +int wolfSSL_BIO_meth_set_write(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_write_cb biom_write) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_set_write"); + if (biom && biom->custom) { + biom->custom->writeCb = biom_write; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + +int wolfSSL_BIO_meth_set_read(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_read_cb biom_read) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_set_read"); + if (biom && biom->custom) { + biom->custom->readCb = biom_read; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + +int wolfSSL_BIO_meth_set_puts(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_puts_cb biom_puts) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_set_puts"); + if (biom && biom->custom) { + biom->custom->putsCb = biom_puts; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + +int wolfSSL_BIO_meth_set_gets(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_gets_cb biom_gets) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_set_gets"); + if (biom && biom->custom) { + biom->custom->getsCb = biom_gets; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + +int wolfSSL_BIO_meth_set_ctrl(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_get_ctrl_cb biom_ctrl) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_set_ctrl"); + if (biom && biom->custom) { + biom->custom->ctrlCb = biom_ctrl; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + +int wolfSSL_BIO_meth_set_create(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_create_cb biom_create) +{ + WOLFSSL_ENTER("wolfSSL_BIO_meth_set_create"); + if (biom && biom->custom) { + biom->custom->createCb = biom_create; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + +int wolfSSL_BIO_meth_set_destroy(WOLFSSL_BIO_METHOD *biom, + wolfSSL_BIO_meth_destroy_cb biom_destroy) +{ + WOLFSSL_STUB("wolfSSL_BIO_meth_set_destroy"); + if (biom && biom->custom) { + biom->custom->freeCb = biom_destroy; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; +} + + #endif /* WOLFSSL_BIO_INCLUDED */ diff --git a/src/internal.c b/src/internal.c index 4832458b3..c87385d3e 100644 --- a/src/internal.c +++ b/src/internal.c @@ -3371,6 +3371,10 @@ void InitX509(WOLFSSL_X509* x509, int dynamicFlag, void* heap) InitX509Name(&x509->issuer, 0); InitX509Name(&x509->subject, 0); x509->dynamicMemory = (byte)dynamicFlag; + #if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL) + x509->refCount = 1; + wc_InitMutex(&x509->refMutex); + #endif } @@ -3421,6 +3425,18 @@ void FreeX509(WOLFSSL_X509* x509) x509->extKeyUsageSrc= NULL; } #endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */ + #if defined(OPENSSL_ALL) + if (x509->algor.algorithm) { + wolfSSL_ASN1_OBJECT_free(x509->algor.algorithm); + x509->algor.algorithm = NULL; + } + if (x509->key.algor) { + wolfSSL_ASN1_OBJECT_free(x509->key.algor->algorithm); + x509->key.algor->algorithm = NULL; + } + XFREE(x509->key.algor, NULL, DYNAMIC_TYPE_OPENSSL); + x509->key.algor = NULL; + #endif /* OPENSSL_ALL */ if (x509->altNames) { FreeAltNames(x509->altNames, x509->heap); x509->altNames = NULL; @@ -5373,6 +5389,9 @@ int InitSSL(WOLFSSL* ssl, WOLFSSL_CTX* ctx, int writeDup) WOLFSSL_MSG("Suites Memory error"); return MEMORY_E; } + #ifdef OPENSSL_ALL + ssl->suites->stack = NULL; + #endif #ifdef SINGLE_THREADED ssl->options.ownSuites = 1; #endif @@ -5727,6 +5746,23 @@ void FreeKeyExchange(WOLFSSL* ssl) #endif } + +/* Free up all memory used by Suites structure from WOLFSSL */ +void FreeSuites(WOLFSSL* ssl) +{ +#ifdef SINGLE_THREADED + if (ssl->options.ownSuites) +#endif + { + #ifdef OPENSSL_ALL + wolfSSL_sk_SSL_CIPHER_free(ssl->suites->stack); + #endif + XFREE(ssl->suites, ssl->heap, DYNAMIC_TYPE_SUITES); + } + ssl->suites = NULL; +} + + /* In case holding SSL object in array and don't want to free actual ssl */ void SSL_ResourceFree(WOLFSSL* ssl) { @@ -5743,14 +5779,7 @@ void SSL_ResourceFree(WOLFSSL* ssl) wc_FreeRng(ssl->rng); XFREE(ssl->rng, ssl->heap, DYNAMIC_TYPE_RNG); } -#ifdef SINGLE_THREADED - if (ssl->options.ownSuites) -#endif - { - XFREE(ssl->suites, ssl->heap, DYNAMIC_TYPE_SUITES); - } - ssl->suites = NULL; - + FreeSuites(ssl); FreeHandshakeHashes(ssl); XFREE(ssl->buffers.domainName.buffer, ssl->heap, DYNAMIC_TYPE_DOMAIN); @@ -5965,7 +5994,7 @@ void FreeHandshakeResources(WOLFSSL* ssl) #ifdef HAVE_SECURE_RENEGOTIATION if (ssl->secure_renegotiation && ssl->secure_renegotiation->enabled) { WOLFSSL_MSG("Secure Renegotiation needs to retain handshake resources"); - #ifdef KEEP_PEER_CERT + #if defined(KEEP_PEER_CERT) && !defined(WOLFSSL_APACHE_HTTPD) /* free peer cert in preparation for new handshake */ FreeX509(&ssl->peerCert); #endif @@ -5981,15 +6010,10 @@ void FreeHandshakeResources(WOLFSSL* ssl) if (!ssl->options.tls1_3) #endif { - /* suites */ -#ifdef SINGLE_THREADED - if (ssl->options.ownSuites) -#endif - { - XFREE(ssl->suites, ssl->heap, DYNAMIC_TYPE_SUITES); - } - ssl->suites = NULL; - + #ifndef OPENSSL_ALL + /* free suites unless using compatibility layer */ + FreeSuites(ssl); + #endif /* hsHashes */ FreeHandshakeHashes(ssl); } @@ -8883,18 +8907,18 @@ int CopyDecodedToX509(WOLFSSL_X509* x509, DecodedCert* dCert) { int minSz = min(dCert->beforeDateLen, MAX_DATE_SZ); if (minSz > 0) { - x509->notBeforeSz = minSz; - XMEMCPY(x509->notBefore, dCert->beforeDate, minSz); + x509->notBefore.length = minSz; + XMEMCPY(x509->notBefore.data, dCert->beforeDate, minSz); } else - x509->notBeforeSz = 0; + x509->notBefore.length = 0; minSz = min(dCert->afterDateLen, MAX_DATE_SZ); if (minSz > 0) { - x509->notAfterSz = minSz; - XMEMCPY(x509->notAfter, dCert->afterDate, minSz); + x509->notAfter.length = minSz; + XMEMCPY(x509->notAfter.data, dCert->afterDate, minSz); } else - x509->notAfterSz = 0; + x509->notAfter.length = 0; } if (dCert->publicKey != NULL && dCert->pubKeySize != 0) { @@ -8907,6 +8931,9 @@ int CopyDecodedToX509(WOLFSSL_X509* x509, DecodedCert* dCert) } else ret = MEMORY_E; +#if defined(OPENSSL_ALL) + x509->key.pubKeyOID = dCert->keyOID; +#endif } if (dCert->signature != NULL && dCert->sigLength != 0 && @@ -8921,6 +8948,11 @@ int CopyDecodedToX509(WOLFSSL_X509* x509, DecodedCert* dCert) x509->sig.length = dCert->sigLength; x509->sigOID = dCert->signatureOID; } +#if defined(OPENSSL_ALL) + if (x509->algor.algorithm == NULL) { + x509->algor.algorithm = wolfSSL_OBJ_nid2obj(dCert->signatureOID); + } +#endif } /* store cert for potential retrieval */ @@ -9253,6 +9285,10 @@ static int DoVerifyCallback(WOLFSSL* ssl, int ret, ProcPeerCertArgs* args) ret == ASN_BEFORE_DATE_E) { alertWhy = certificate_expired; } +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) + else if (ret == CRL_CERT_REVOKED) + alertWhy = certificate_revoked; +#endif } else { verify_ok = 1; @@ -9350,7 +9386,9 @@ static int DoVerifyCallback(WOLFSSL* ssl, int ret, ProcPeerCertArgs* args) store->userCtx = ssl->verifyCbCtx; store->certs = args->certs; store->totalCerts = args->totalCerts; - store->ex_data = ssl; + #if defined(HAVE_EX_DATA) || defined(FORTRESS) + store->ex_data[0] = ssl; + #endif #if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER) if (ssl->ctx->x509_store_pt != NULL) { @@ -10218,13 +10256,15 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx, if (IsEncryptionOn(ssl, 0)) { /* compare against previous time */ - if (XMEMCMP(args->dCert->subjectHash, - ssl->secure_renegotiation->subject_hash, - KEYID_SIZE) != 0) { - WOLFSSL_MSG( - "Peer sent different cert during scr, fatal"); - args->fatal = 1; - ret = SCR_DIFFERENT_CERT_E; + if (ssl->secure_renegotiation->subject_hash_set) { + if (XMEMCMP(args->dCert->subjectHash, + ssl->secure_renegotiation->subject_hash, + KEYID_SIZE) != 0) { + WOLFSSL_MSG( + "Peer sent different cert during scr, fatal"); + args->fatal = 1; + ret = SCR_DIFFERENT_CERT_E; + } } } @@ -10232,6 +10272,7 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx, if (args->fatal == 0) { XMEMCPY(ssl->secure_renegotiation->subject_hash, args->dCert->subjectHash, KEYID_SIZE); + ssl->secure_renegotiation->subject_hash_set = 1; } } #endif /* HAVE_SECURE_RENEGOTIATION */ @@ -10331,9 +10372,21 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx, #ifdef KEEP_PEER_CERT if (args->fatal == 0) { + int copyRet = 0; + + #ifdef HAVE_SECURE_RENEGOTIATION + if (ssl->secure_renegotiation && + ssl->secure_renegotiation->enabled) { + #if defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD) + /* free old peer cert */ + if (ssl->peerCert.issuer.sz) + FreeX509(&ssl->peerCert); + #endif + } + #endif + /* set X509 format for peer cert */ - int copyRet = CopyDecodedToX509(&ssl->peerCert, - args->dCert); + copyRet = CopyDecodedToX509(&ssl->peerCert, args->dCert); if (copyRet == MEMORY_E) { args->fatal = 1; } @@ -17059,6 +17112,9 @@ const char* wolfSSL_ERR_reason_error_string(unsigned long e) return "Invalid MAC size is specified. \ TSIP can only handle SHA1 and SHA256 digest size"; + case CLIENT_CERT_CB_ERROR: + return "Error importing client cert or key from callback"; + default : return "unknown error number"; } @@ -19115,6 +19171,11 @@ exit_dpk: { word16 len; word32 begin = *inOutIdx; + #ifdef OPENSSL_EXTRA + int ret; + WOLFSSL_X509* x509 = NULL; + WOLFSSL_EVP_PKEY* pkey = NULL; + #endif WOLFSSL_START(WC_FUNC_CERTIFICATE_REQUEST_DO); WOLFSSL_ENTER("DoCertificateRequest"); @@ -19195,6 +19256,26 @@ exit_dpk: len -= OPAQUE16_LEN + dnSz; } + #ifdef OPENSSL_EXTRA + /* call client cert callback if no cert has been loaded */ + if ((ssl->ctx->CBClientCert != NULL) && + (!ssl->buffers.certificate || !ssl->buffers.certificate->buffer)) { + + ret = ssl->ctx->CBClientCert(ssl, &x509, &pkey); + if (ret == 1) { + if ((wolfSSL_use_certificate(ssl, x509) != WOLFSSL_SUCCESS) || + (wolfSSL_use_PrivateKey(ssl, pkey) != WOLFSSL_SUCCESS)) { + return CLIENT_CERT_CB_ERROR; + } + wolfSSL_X509_free(x509); + wolfSSL_EVP_PKEY_free(pkey); + + } else if (ret < 0) { + return WOLFSSL_ERROR_WANT_X509_LOOKUP; + } + } + #endif + /* don't send client cert or cert verify if user hasn't provided cert and private key */ if (ssl->buffers.certificate && ssl->buffers.certificate->buffer) { @@ -21535,7 +21616,7 @@ int SendClientKeyExchange(WOLFSSL* ssl) #ifdef WOLFSSL_ASYNC_CRYPT && ret != WC_PENDING_E #endif - ) { + && !ssl->options.keepResources) { FreeKey(ssl, DYNAMIC_TYPE_ECC, (void**)&ssl->peerEccKey); ssl->peerEccKeyPresent = 0; diff --git a/src/ocsp.c b/src/ocsp.c index 4c8a6b3e4..a71652347 100644 --- a/src/ocsp.c +++ b/src/ocsp.c @@ -491,7 +491,8 @@ int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, return ret; } -#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) +#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) || \ + defined(WOLFSSL_APACHE_HTTPD) int wolfSSL_OCSP_resp_find_status(WOLFSSL_OCSP_BASICRESP *bs, WOLFSSL_OCSP_CERTID* id, int* status, int* reason, @@ -865,8 +866,207 @@ WOLFSSL_OCSP_ONEREQ* wolfSSL_OCSP_request_add0_id(OcspRequest *req, return req; } +WOLFSSL_OCSP_CERTID* wolfSSL_OCSP_CERTID_dup(WOLFSSL_OCSP_CERTID* id) +{ + WOLFSSL_OCSP_CERTID* certId; + + if (id == NULL) { + return NULL; + } + + certId = (WOLFSSL_OCSP_CERTID*)XMALLOC(sizeof(WOLFSSL_OCSP_CERTID), + id->heap, DYNAMIC_TYPE_OPENSSL); + if (certId) { + XMEMCPY(certId, id, sizeof(WOLFSSL_OCSP_CERTID)); + } + return certId; +} #endif +#if defined(OPENSSL_ALL) || defined(APACHE_HTTPD) +int wolfSSL_i2d_OCSP_REQUEST_bio(WOLFSSL_BIO* out, + WOLFSSL_OCSP_REQUEST *req) +{ + int size = -1; + unsigned char* data = NULL; + + WOLFSSL_ENTER("wolfSSL_i2d_OCSP_REQUEST_bio"); + if (out == NULL || req == NULL) + return WOLFSSL_FAILURE; + + size = wolfSSL_i2d_OCSP_REQUEST(req, NULL); + if (size > 0) + data = (unsigned char*) XMALLOC(size,NULL,DYNAMIC_TYPE_TMP_BUFFER); + if (data != NULL) + size = wolfSSL_i2d_OCSP_REQUEST(req, &data); + + if (size <= 0) { + XFREE(data,NULL,DYNAMIC_TYPE_TMP_BUFFER); + return WOLFSSL_FAILURE; + } + + if (wolfSSL_BIO_write(out,data,size) == (int)size) { + XFREE(data,NULL,DYNAMIC_TYPE_TMP_BUFFER); + return WOLFSSL_SUCCESS; + } + + return WOLFSSL_FAILURE; +} +#endif /* OPENSSL_ALL || APACHE_HTTPD */ + +#ifdef OPENSSL_EXTRA +#ifndef NO_WOLFSSL_STUB +int wolfSSL_OCSP_REQUEST_add_ext(OcspRequest* req, WOLFSSL_X509_EXTENSION* ext, + int idx) +{ + WOLFSSL_STUB("wolfSSL_OCSP_REQUEST_add_ext"); + (void)req; + (void)ext; + (void)idx; + return WOLFSSL_FATAL_ERROR; +} +#endif + +#ifndef NO_WOLFSSL_STUB +OcspResponse* wolfSSL_OCSP_response_create(int status, + WOLFSSL_OCSP_BASICRESP* bs) +{ + WOLFSSL_STUB("wolfSSL_OCSP_response_create"); + (void)status; + (void)bs; + return NULL; +} +#endif + +#ifndef NO_WOLFSSL_STUB +const char* wolfSSL_OCSP_crl_reason_str(long s) +{ + WOLFSSL_STUB("wolfSSL_OCSP_crl_reason_str"); + (void)s; + return NULL; +} +#endif + +/* Returns elements of an OCSP_CERTID struct. Currently only supports + * returning the serial number, and returns an error if user requests + * any of name, pmd, and/or keyHash. + * Return 1 on success, 0 on failure */ +int wolfSSL_OCSP_id_get0_info(WOLFSSL_ASN1_STRING **name, + WOLFSSL_ASN1_OBJECT **pmd, WOLFSSL_ASN1_STRING **keyHash, + WOLFSSL_ASN1_INTEGER **serial, WOLFSSL_OCSP_CERTID *cid) +{ + int i = 0; + WOLFSSL_ASN1_INTEGER* ser; + + WOLFSSL_ENTER("wolfSSL_OCSP_id_get0_info"); + + if (cid == NULL) + return 0; + + /* build up ASN1_INTEGER for serial */ + if (serial != NULL) { + ser = wolfSSL_ASN1_INTEGER_new(); + if (ser == NULL) + return 0; + + if (cid->serialSz > (WOLFSSL_ASN1_INTEGER_MAX - 2)) { + /* allocate data buffer, +2 for type and length */ + ser->data = (unsigned char*)XMALLOC(cid->serialSz + 2, NULL, + DYNAMIC_TYPE_OPENSSL); + if (ser->data == NULL) { + wolfSSL_ASN1_INTEGER_free(ser); + return 0; + } + ser->dataMax = cid->serialSz + 2; + ser->isDynamic = 1; + } + + ser->data[i++] = ASN_INTEGER; + i += SetLength(cid->serialSz, ser->data + i); + XMEMCPY(&ser->data[i], cid->serial, cid->serialSz); + + cid->serialInt = ser; + *serial = cid->serialInt; + } + + /* Not needed for Apache, return error if user is requesting */ + if (name != NULL || pmd != NULL || keyHash != NULL) { + if (name != NULL) + *name = NULL; + + if (pmd != NULL) + *pmd = NULL; + + if (keyHash != NULL) + *keyHash = NULL; + return 0; + } + + return 1; +} + +#ifndef NO_WOLFSSL_STUB +int wolfSSL_OCSP_request_add1_nonce(OcspRequest* req, unsigned char* val, + int sz) +{ + WOLFSSL_STUB("wolfSSL_OCSP_request_add1_nonce"); + (void)req; + (void)val; + (void)sz; + return WOLFSSL_FATAL_ERROR; +} +#endif + +/* Returns result of OCSP nonce comparison. Return values: + * 1 - nonces are both present and equal + * 2 - both nonces are absent + * 3 - nonce only present in response + * -1 - nonce only present in request + * 0 - both nonces present and equal + */ +int wolfSSL_OCSP_check_nonce(OcspRequest* req, WOLFSSL_OCSP_BASICRESP* bs) +{ + byte* reqNonce = NULL; + byte* rspNonce = NULL; + int reqNonceSz = 0; + int rspNonceSz = 0; + + WOLFSSL_ENTER("wolfSSL_OCSP_check_nonce"); + + if (req != NULL) { + reqNonce = req->nonce; + reqNonceSz = req->nonceSz; + } + + if (bs != NULL) { + rspNonce = bs->nonce; + rspNonceSz = bs->nonceSz; + } + + /* nonce absent in both req and rsp */ + if (reqNonce == NULL && rspNonce == NULL) + return 2; + + /* nonce present in rsp only */ + if (reqNonce == NULL && rspNonce != NULL) + return 3; + + /* nonce present in req only */ + if (reqNonce != NULL && rspNonce == NULL) + return -1; + + /* nonces are present and equal, return 1. Extra NULL check for fixing + scan-build warning. */ + if (reqNonceSz == rspNonceSz && reqNonce && rspNonce) { + if (XMEMCMP(reqNonce, rspNonce, reqNonceSz) == 0) + return 1; + } + + /* nonces are present but not equal */ + return 0; +} +#endif /* OPENSSL_EXTRA */ + #else /* HAVE_OCSP */ diff --git a/src/ssl.c b/src/ssl.c index 4e37408ee..3615b431b 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -25,6 +25,11 @@ #endif #include +#if defined(OPENSSL_EXTRA) && !defined(_WIN32) + /* turn on GNU extensions for vasprintf with wolfSSL_BIO_printf */ + #undef _GNU_SOURCE + #define _GNU_SOURCE +#endif #ifndef WOLFCRYPT_ONLY @@ -49,6 +54,10 @@ && !defined(HAVE_ED25519) #error "No cipher suites defined because DH disabled, ECC disabled, and no static suites defined. Please see top of README" #endif + #ifdef WOLFSSL_CERT_GEN + /* need access to Cert struct for creating certificate */ + #include + #endif #endif #if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL) || \ @@ -2463,6 +2472,7 @@ int wolfSSL_CTX_UseSecureRenegotiation(WOLFSSL_CTX* ctx) int wolfSSL_Rehandshake(WOLFSSL* ssl) { int ret; + WOLFSSL_ENTER("wolfSSL_Rehandshake"); if (ssl == NULL) return BAD_FUNC_ARG; @@ -2501,7 +2511,7 @@ int wolfSSL_Rehandshake(WOLFSSL* ssl) ssl->options.serverState = NULL_STATE; ssl->options.clientState = NULL_STATE; ssl->options.connectState = CONNECT_BEGIN; - ssl->options.acceptState = ACCEPT_BEGIN; + ssl->options.acceptState = ACCEPT_BEGIN_RENEG; ssl->options.handShakeState = NULL_STATE; ssl->options.processReply = 0; /* TODO, move states in internal.h */ @@ -2526,6 +2536,7 @@ int wolfSSL_Rehandshake(WOLFSSL* ssl) } } ret = wolfSSL_negotiate(ssl); + ssl->secure_rene_count++; return ret; } @@ -2559,6 +2570,15 @@ int wolfSSL_SecureResume(WOLFSSL* ssl) #endif /* NO_WOLFSSL_CLIENT */ +long wolfSSL_SSL_get_secure_renegotiation_support(WOLFSSL* ssl) +{ + WOLFSSL_ENTER("wolfSSL_SSL_get_secure_renegotiation_support"); + + if (!ssl) + return WOLFSSL_FAILURE; + return ssl->secure_renegotiation->enabled; +} + #endif /* HAVE_SECURE_RENEGOTIATION */ /* Session Ticket */ @@ -3803,7 +3823,6 @@ void wolfSSL_ERR_dump_errors_fp(XFILE fp) #endif #endif - int wolfSSL_pending(WOLFSSL* ssl) { WOLFSSL_ENTER("SSL_pending"); @@ -3872,9 +3891,11 @@ static int SetMinVersionHelper(byte* minVersion, int version) #ifndef NO_TLS #ifndef NO_OLD_TLS + #ifdef WOLFSSL_ALLOW_TLSV10 case WOLFSSL_TLSV1: *minVersion = TLSv1_MINOR; break; + #endif case WOLFSSL_TLSV1_1: *minVersion = TLSv1_1_MINOR; @@ -6194,6 +6215,8 @@ int ProcessFile(WOLFSSL_CTX* ctx, const char* fname, int format, int type, long sz = 0; XFILE file; void* heapHint = wolfSSL_CTX_GetHeap(ctx, ssl); + const char* header = NULL; + const char* footer = NULL; (void)crl; (void)heapHint; @@ -6226,6 +6249,29 @@ int ProcessFile(WOLFSSL_CTX* ctx, const char* fname, int format, int type, if ( (ret = (int)XFREAD(myBuffer, 1, sz, file)) != sz) ret = WOLFSSL_BAD_FILE; else { + /* Try to detect type by parsing cert header and footer */ + if (type == DETECT_CERT_TYPE) { + if (wc_PemGetHeaderFooter(CA_TYPE, &header, &footer) == 0 && + (XSTRNSTR((char*)myBuffer, header, (int)sz) != NULL)) { + type = CA_TYPE; + } +#ifdef HAVE_CRL + else if (wc_PemGetHeaderFooter(CRL_TYPE, &header, &footer) == 0 && + (XSTRNSTR((char*)myBuffer, header, (int)sz) != NULL)) { + type = CRL_TYPE; + } +#endif + else if (wc_PemGetHeaderFooter(CERT_TYPE, &header, &footer) == 0 && + (XSTRNSTR((char*)myBuffer, header, (int)sz) != NULL)) { + type = CERT_TYPE; + } + else { + WOLFSSL_MSG("Failed to detect certificate type"); + if (dynamic) + XFREE(myBuffer, heapHint, DYNAMIC_TYPE_FILE); + return WOLFSSL_BAD_CERTTYPE; + } + } if ((type == CA_TYPE || type == TRUSTED_PEER_TYPE) && format == WOLFSSL_FILETYPE_PEM) ret = ProcessChainBuffer(ctx, myBuffer, sz, format, type, ssl, @@ -6449,7 +6495,7 @@ int wolfSSL_CertManagerLoadCA(WOLFSSL_CERT_MANAGER* cm, const char* file, ret = wolfSSL_CTX_load_verify_locations(tmp, file, path); - /* don't loose our good one */ + /* don't lose our good one */ tmp->cm = NULL; wolfSSL_CTX_free(tmp); @@ -6603,7 +6649,6 @@ int wolfSSL_CertManagerLoadCRL(WOLFSSL_CERT_MANAGER* cm, const char* path, return LoadCRL(cm->crl, path, type, monitor); } - int wolfSSL_EnableCRL(WOLFSSL* ssl, int options) { WOLFSSL_ENTER("wolfSSL_EnableCRL"); @@ -6623,7 +6668,6 @@ int wolfSSL_DisableCRL(WOLFSSL* ssl) return BAD_FUNC_ARG; } - int wolfSSL_LoadCRL(WOLFSSL* ssl, const char* path, int type, int monitor) { WOLFSSL_ENTER("wolfSSL_LoadCRL"); @@ -7338,30 +7382,6 @@ WOLFSSL_EVP_PKEY* wolfSSL_d2i_PrivateKey(int type, WOLFSSL_EVP_PKEY** out, return local; } -#ifndef NO_WOLFSSL_STUB -long wolfSSL_ctrl(WOLFSSL* ssl, int cmd, long opt, void* pt) -{ - WOLFSSL_STUB("SSL_ctrl"); - (void)ssl; - (void)cmd; - (void)opt; - (void)pt; - return WOLFSSL_FAILURE; -} -#endif - -#ifndef NO_WOLFSSL_STUB -long wolfSSL_CTX_ctrl(WOLFSSL_CTX* ctx, int cmd, long opt, void* pt) -{ - WOLFSSL_STUB("SSL_CTX_ctrl"); - (void)ctx; - (void)cmd; - (void)opt; - (void)pt; - return WOLFSSL_FAILURE; -} -#endif - #ifndef NO_CERTS int wolfSSL_check_private_key(const WOLFSSL* ssl) @@ -8008,18 +8028,6 @@ int wolfSSL_X509V3_EXT_print(WOLFSSL_BIO *out, WOLFSSL_X509_EXTENSION *ext, return rc; } - -/* Returns pointer to ASN1_OBJECT from a X509_EXTENSION object */ -WOLFSSL_ASN1_OBJECT* wolfSSL_X509_EXTENSION_get_object(WOLFSSL_X509_EXTENSION* ex) -{ - WOLFSSL_ENTER("wolfSSL_X509_EXTENSION_get_object"); - if(ex == NULL){ - return NULL; - } - WOLFSSL_LEAVE("wolfSSL_X509_EXTENSION_get_object", WOLFSSL_SUCCESS); - return ex->obj; -} - /* Returns crit flag in X509_EXTENSION object */ int wolfSSL_X509_EXTENSION_get_critical(const WOLFSSL_X509_EXTENSION* ex) { @@ -8029,15 +8037,6 @@ int wolfSSL_X509_EXTENSION_get_critical(const WOLFSSL_X509_EXTENSION* ex) return ex->crit; } -/* Returns pointer to ASN1_STRING in X509_EXTENSION object */ -WOLFSSL_ASN1_STRING* wolfSSL_X509_EXTENSION_get_data(WOLFSSL_X509_EXTENSION* ex) -{ - WOLFSSL_ENTER("wolfSSL_X509_EXTENSION_get_data"); - if (ex == NULL) - return NULL; - return &ex->value; -} - /* Creates v3_ext_method for a given X509v3 extension * * ex : The X509_EXTENSION used to create v3_ext_method. If the extension is @@ -8508,6 +8507,7 @@ void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, { WOLFSSL_STACK* sk = NULL; WOLFSSL_ASN1_OBJECT* obj = NULL; + WOLFSSL_GENERAL_NAME* gn = NULL; WOLFSSL_ENTER("wolfSSL_X509_get_ext_d2i"); @@ -8538,16 +8538,34 @@ void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, } obj->type = BASIC_CA_OID; obj->grp = oidCertExtType; + obj->nid = nid; obj->dynamic |= WOLFSSL_ASN1_DYNAMIC; + #if defined(WOLFSSL_APACHE_HTTPD) + obj->ca = x509->basicConstSet; + #endif } else { WOLFSSL_MSG("No Basic Constraint set"); } - break; + + /* Stack wasn't used, so free before returning obj */ + wolfSSL_sk_ASN1_OBJECT_free(sk); + sk = NULL; + + return obj; case ALT_NAMES_OID: { DNS_entry* dns = NULL; + /* Free ASN1_OBJECT stack and malloc GENERAL_NAME stack */ + wolfSSL_sk_ASN1_OBJECT_free(sk); + sk = (WOLF_STACK_OF(WOLFSSL_GENERAL_NAME)*)XMALLOC( + sizeof(WOLF_STACK_OF(WOLFSSL_GENERAL_NAME)), NULL, + DYNAMIC_TYPE_ASN1); + if (sk == NULL) { + return NULL; + } + XMEMSET(sk, 0, sizeof(WOLF_STACK_OF(WOLFSSL_GENERAL_NAME))); sk->type = STACK_TYPE_GEN_NAME; if (x509->subjAltNameSet && x509->altNames != NULL) { @@ -8562,30 +8580,33 @@ void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, } dns = x509->altNames; + /* Currenlty only support GEN_DNS type */ while (dns != NULL) { - obj = wolfSSL_ASN1_OBJECT_new(); - if (obj == NULL) { - WOLFSSL_MSG("Issue creating WOLFSSL_ASN1_OBJECT struct"); - wolfSSL_sk_ASN1_OBJECT_free(sk); + gn = wolfSSL_GENERAL_NAME_new(); + if (gn == NULL) { + WOLFSSL_MSG("Error creating GENERAL_NAME"); + wolfSSL_sk_free(sk); + return NULL; + } + + gn->type = dns->type; + gn->d.ia5->length = (int)XSTRLEN(dns->name); + if (wolfSSL_ASN1_STRING_set(gn->d.ia5, dns->name, + gn->d.ia5->length) != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("ASN1_STRING_set failed"); + wolfSSL_GENERAL_NAME_free(gn); + wolfSSL_sk_free(sk); return NULL; } - obj->type = dns->type; - obj->grp = oidCertExtType; - obj->obj = (byte*)dns->name; - obj->dynamic |= WOLFSSL_ASN1_DYNAMIC; - obj->dynamic &= ~WOLFSSL_ASN1_DYNAMIC_DATA ; - /* set app dereferenced pointers */ - obj->d.ia5_internal.data = dns->name; - obj->d.ia5_internal.length = (int)XSTRLEN(dns->name); dns = dns->next; /* last dns in list add at end of function */ if (dns != NULL) { - if (wolfSSL_sk_ASN1_OBJECT_push(sk, obj) - != WOLFSSL_SUCCESS) { + if (wolfSSL_sk_GENERAL_NAME_push(sk, gn) != + WOLFSSL_SUCCESS) { WOLFSSL_MSG("Error pushing ASN1 object onto stack"); - wolfSSL_ASN1_OBJECT_free(obj); - wolfSSL_sk_ASN1_OBJECT_free(sk); + wolfSSL_GENERAL_NAME_free(gn); + wolfSSL_sk_free(sk); sk = NULL; } } @@ -8862,6 +8883,14 @@ void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, sk = NULL; } } + else if (gn != NULL) { + if (wolfSSL_sk_GENERAL_NAME_push(sk, gn) != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Error pushing GENERAL_NAME object onto stack"); + wolfSSL_GENERAL_NAME_free(gn); + wolfSSL_sk_free(sk); + sk = NULL; + } + } else { /* no ASN1 object found for extension, free stack */ wolfSSL_sk_ASN1_OBJECT_free(sk); sk = NULL; @@ -8872,6 +8901,61 @@ void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, return sk; } +#ifndef NO_WOLFSSL_STUB +int wolfSSL_X509_add_ext(WOLFSSL_X509 *x509, WOLFSSL_X509_EXTENSION *ext, int loc) +{ + WOLFSSL_STUB("wolfSSL_X509_add_ext"); + (void)x509; + (void)ext; + (void)loc; + return WOLFSSL_FAILURE; +} + +/* currently LHASH is not implemented (and not needed for Apache port) */ +WOLFSSL_X509_EXTENSION* wolfSSL_X509V3_EXT_conf_nid( + WOLF_LHASH_OF(CONF_VALUE)* conf, WOLFSSL_X509V3_CTX* ctx, int nid, + char* value) +{ + WOLFSSL_STUB("wolfSSL_X509V3_EXT_conf_nid"); + + if (conf != NULL) { + WOLFSSL_MSG("Handling LHASH not implemented yet"); + return NULL; + } + + (void)conf; + (void)ctx; + (void)nid; + (void)value; + return NULL; +} + +void wolfSSL_X509V3_set_ctx_nodb(WOLFSSL_X509V3_CTX* ctx) +{ + WOLFSSL_STUB("wolfSSL_X509V3_set_ctx_nodb"); + (void)ctx; +} +#endif /* !NO_WOLFSSL_STUB */ + +/* Returns pointer to ASN1_OBJECT from an X509_EXTENSION object */ +WOLFSSL_ASN1_OBJECT* wolfSSL_X509_EXTENSION_get_object \ + (WOLFSSL_X509_EXTENSION* ext) +{ + WOLFSSL_ENTER("wolfSSL_X509_EXTENSION_get_object"); + if(ext == NULL) + return NULL; + return ext->obj; +} + +/* Returns pointer to ASN1_STRING in X509_EXTENSION object */ +WOLFSSL_ASN1_STRING* wolfSSL_X509_EXTENSION_get_data(WOLFSSL_X509_EXTENSION* ext) +{ + WOLFSSL_ENTER("wolfSSL_X509_EXTENSION_get_data"); + if (ext == NULL) + return NULL; + return &ext->value; +} + /* this function makes the assumption that out buffer is big enough for digest*/ int wolfSSL_EVP_Digest(unsigned char* in, int inSz, unsigned char* out, unsigned int* outSz, const WOLFSSL_EVP_MD* evp, @@ -8881,18 +8965,24 @@ int wolfSSL_EVP_Digest(unsigned char* in, int inSz, unsigned char* out, int hashType = WC_HASH_TYPE_NONE; int hashSz; - (void)eng; + WOLFSSL_ENTER("wolfSSL_EVP_Digest"); + if (in == NULL || out == NULL || evp == NULL) { + WOLFSSL_MSG("Null argument passed in"); + return WOLFSSL_FAILURE; + } err = wolfSSL_EVP_get_hashinfo(evp, &hashType, &hashSz); if (err != WOLFSSL_SUCCESS) return err; - *outSz = hashSz; - - if (wc_Hash((enum wc_HashType)hashType, in, inSz, out, *outSz) != 0) { + if (wc_Hash((enum wc_HashType)hashType, in, inSz, out, hashSz) != 0) { return WOLFSSL_FAILURE; } + if (outSz != NULL) + *outSz = hashSz; + + (void)eng; return WOLFSSL_SUCCESS; } @@ -8900,14 +8990,24 @@ int wolfSSL_EVP_Digest(unsigned char* in, int inSz, unsigned char* out, int wolfSSL_X509_digest(const WOLFSSL_X509* x509, const WOLFSSL_EVP_MD* digest, unsigned char* buf, unsigned int* len) { + int ret; + WOLFSSL_ENTER("wolfSSL_X509_digest"); if (x509 == NULL || digest == NULL) { + WOLFSSL_MSG("Null argument found"); return WOLFSSL_FAILURE; } - return wolfSSL_EVP_Digest(x509->derCert->buffer, x509->derCert->length, buf, + if (x509->derCert == NULL) { + WOLFSSL_MSG("No DER certificate stored in X509"); + return WOLFSSL_FAILURE; + } + + ret = wolfSSL_EVP_Digest(x509->derCert->buffer, x509->derCert->length, buf, len, digest, NULL); + WOLFSSL_LEAVE("wolfSSL_X509_digest", ret); + return ret; } @@ -9226,8 +9326,9 @@ void wolfSSL_CTX_set_verify(WOLFSSL_CTX* ctx, int mode, VerifyCallback vc) ctx->verifyPeer = 0; /* in case previously set */ } - if (mode & WOLFSSL_VERIFY_FAIL_IF_NO_PEER_CERT) + if (mode & WOLFSSL_VERIFY_FAIL_IF_NO_PEER_CERT) { ctx->failNoCert = 1; + } if (mode & WOLFSSL_VERIFY_FAIL_EXCEPT_PSK) { ctx->failNoCert = 0; /* fail on all is set to fail on PSK */ @@ -9265,6 +9366,20 @@ void wolfSSL_set_verify(WOLFSSL* ssl, int mode, VerifyCallback vc) ssl->verifyCallback = vc; } +void wolfSSL_set_verify_result(WOLFSSL *ssl, long v) +{ + WOLFSSL_ENTER("wolfSSL_set_verify_result"); + + if (ssl == NULL) + return; + +#ifdef OPENSSL_ALL + ssl->verifyCallbackResult = v; +#else + (void)v; + WOLFSSL_STUB("wolfSSL_set_verify_result"); +#endif +} /* store user ctx for verify callback */ void wolfSSL_SetCertCbCtx(WOLFSSL* ssl, void* ctx) @@ -10204,6 +10319,117 @@ int CM_GetCertCacheMemSize(WOLFSSL_CERT_MANAGER* cm) #endif /* PERSIST_CERT_CACHE */ #endif /* NO_CERTS */ +#ifdef OPENSSL_EXTRA + + +/* removes all cipher suites from the list that contain "toRemove" + * returns the new list size on success + */ +static int wolfSSL_remove_ciphers(char* list, int sz, const char* toRemove) +{ + int idx = 0; + char* next = (char*)list; + int totalSz = sz; + + if (list == NULL) { + return 0; + } + + do { + char* current = next; + char name[MAX_SUITE_NAME + 1]; + word32 length; + + next = XSTRSTR(next, ":"); + length = min(sizeof(name), !next ? (word32)XSTRLEN(current) /* last */ + : (word32)(next - current)); + + XSTRNCPY(name, current, length); + name[(length == sizeof(name)) ? length - 1 : length] = 0; + + if (XSTRSTR(name, toRemove)) { + XMEMMOVE(list + idx, list + idx + length, totalSz - (idx + length)); + totalSz -= length; + list[totalSz] = '\0'; + next = current; + } + else { + idx += length; + } + } while (next++); /* ++ needed to skip ':' */ + + return totalSz; +} + +/* parse some bulk lists like !eNULL / !aNULL + * + * returns WOLFSSL_SUCCESS on success and sets the cipher suite list + */ +static int wolfSSL_parse_cipher_list(WOLFSSL_CTX* ctx, Suites* suites, + const char* list) +{ + int ret = 0; + const int suiteSz = GetCipherNamesSize(); + char* next = (char*)list; + const CipherSuiteInfo* names = GetCipherNames(); + char* localList = NULL; + int sz = 0; + + if (suites == NULL || list == NULL) { + WOLFSSL_MSG("NULL argument"); + return WOLFSSL_FAILURE; + } + + /* does list contain eNULL or aNULL? */ + if (XSTRSTR(list, "aNULL") || XSTRSTR(list, "eNULL")) { + do { + char* current = next; + char name[MAX_SUITE_NAME + 1]; + int i; + word32 length; + + next = XSTRSTR(next, ":"); + length = min(sizeof(name), !next ? (word32)XSTRLEN(current) /*last*/ + : (word32)(next - current)); + + XSTRNCPY(name, current, length); + name[(length == sizeof(name)) ? length - 1 : length] = 0; + + /* check for "not" case */ + if (name[0] == '!') { + /* populate list with all suites if not already created */ + if (localList == NULL) { + for (i = 0; i < suiteSz; i++) { + sz += (int)XSTRLEN(names[i].name) + 2; + } + localList = (char*)XMALLOC(sz, ctx->heap, + DYNAMIC_TYPE_TMP_BUFFER); + if (localList == NULL) { + return WOLFSSL_FAILURE; + } + wolfSSL_get_ciphers(localList, sz); + sz = (int)XSTRLEN(localList); + } + + if (XSTRSTR(name, "eNULL")) { + wolfSSL_remove_ciphers(localList, sz, "-NULL"); + } + } + } + while (next++); /* ++ needed to skip ':' */ + + ret = SetCipherList(ctx, suites, localList); + XFREE(localList, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); + return (ret)? WOLFSSL_SUCCESS : WOLFSSL_FAILURE; + } + else { + return (SetCipherList(ctx, suites, list)) ? WOLFSSL_SUCCESS : + WOLFSSL_FAILURE; + } +} + +#endif + int wolfSSL_CTX_set_cipher_list(WOLFSSL_CTX* ctx, const char* list) { @@ -10223,7 +10449,11 @@ int wolfSSL_CTX_set_cipher_list(WOLFSSL_CTX* ctx, const char* list) XMEMSET(ctx->suites, 0, sizeof(Suites)); } +#ifdef OPENSSL_EXTRA + return wolfSSL_parse_cipher_list(ctx, ctx->suites, list); +#else return (SetCipherList(ctx, ctx->suites, list)) ? WOLFSSL_SUCCESS : WOLFSSL_FAILURE; +#endif } @@ -10242,7 +10472,11 @@ int wolfSSL_set_cipher_list(WOLFSSL* ssl, const char* list) } #endif +#ifdef OPENSSL_EXTRA + return wolfSSL_parse_cipher_list(ssl->ctx, ssl->suites, list); +#else return (SetCipherList(ssl->ctx, ssl->suites, list)) ? WOLFSSL_SUCCESS : WOLFSSL_FAILURE; +#endif } @@ -10920,6 +11154,7 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl, #if defined(OPENSSL_EXTRA) || defined(WOLFSSL_EITHER_SIDE) if (ssl->options.side == WOLFSSL_NEITHER_END) { + WOLFSSL_MSG("Setting WOLFSSL_SSL to be server side"); ssl->error = InitSSL_Side(ssl, WOLFSSL_SERVER_END); if (ssl->error != WOLFSSL_SUCCESS) { WOLFSSL_ERROR(ssl->error); @@ -11020,6 +11255,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl, switch (ssl->options.acceptState) { case ACCEPT_BEGIN : +#ifdef HAVE_SECURE_RENEGOTIATION + case ACCEPT_BEGIN_RENEG: +#endif /* get response */ while (ssl->options.clientState < CLIENT_HELLO_COMPLETE) if ( (ssl->error = ProcessReply(ssl)) < 0) { @@ -13095,7 +13333,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) void wolfSSL_CTX_set_client_CA_list(WOLFSSL_CTX* ctx, WOLF_STACK_OF(WOLFSSL_X509_NAME)* names) { - WOLFSSL_ENTER("wolfSSL_SSL_CTX_set_client_CA_list"); + WOLFSSL_ENTER("wolfSSL_CTX_set_client_CA_list"); #if defined(OPENSSL_EXTRA) || defined(WOLFSSL_EXTRA) if (ctx != NULL) ctx->ca_names = names; @@ -13104,7 +13342,73 @@ int wolfSSL_set_compression(WOLFSSL* ssl) (void)names; #endif } -#endif + + + /* returns the CA's set on server side or the CA's sent from server when + * on client side */ +#if defined(SESSION_CERTS) && defined(OPENSSL_ALL) + WOLF_STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_get_client_CA_list( + const WOLFSSL* ssl) + { + WOLFSSL_ENTER("wolfSSL_get_client_CA_list"); + + if (ssl == NULL) { + WOLFSSL_MSG("Bad argument passed to wolfSSL_get_client_CA_list"); + return NULL; + } + + /* return list of CAs sent from the server */ + if (ssl->options.side == WOLFSSL_CLIENT_END) { + WOLF_STACK_OF(WOLFSSL_X509)* sk; + + sk = wolfSSL_get_peer_cert_chain(ssl); + if (sk != NULL) { + WOLF_STACK_OF(WOLFSSL_X509_NAME)* ret; + WOLFSSL_X509* x509; + + ret = wolfSSL_sk_X509_NAME_new(NULL); + do { + x509 = wolfSSL_sk_X509_pop(sk); + if (x509 != NULL) { + if (wolfSSL_X509_get_isCA(x509)) { + if (wolfSSL_sk_X509_NAME_push(ret, + wolfSSL_X509_get_subject_name(x509)) != 0) { + WOLFSSL_MSG("Error pushing X509 name to stack"); + /* continue on to try other certificates and + * do not fail out here */ + } + } + wolfSSL_X509_free(x509); + } + } while (x509 != NULL); + wolfSSL_sk_X509_free(sk); + return ret; + } + return NULL; + } + else { + /* currently only can be set in the CTX */ + return ssl->ctx->ca_names; + } + } +#endif /* SESSION_CERTS */ + + + #if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA) || \ + defined(WOLFSSL_NGINX) || defined (WOLFSSL_HAPROXY) + /* registers client cert callback, called during handshake if server + requests client auth but user has not loaded client cert/key */ + void wolfSSL_CTX_set_client_cert_cb(WOLFSSL_CTX *ctx, client_cert_cb cb) + { + WOLFSSL_ENTER("wolfSSL_CTX_set_client_cert_cb"); + + if (ctx != NULL) { + ctx->CBClientCert = cb; + } + } + #endif /* OPENSSL_ALL || OPENSSL_EXTRA || WOLFSSL_NGINX || WOLFSSL_HAPROXY */ + +#endif /* OPENSSL_EXTRA || WOLFSSL_EXTRA || HAVE_WEBSERVER */ #if defined(OPENSSL_EXTRA) || defined(WOLFSSL_EXTRA) WOLF_STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_SSL_CTX_get_client_CA_list( @@ -13152,15 +13456,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) break; /* Need a persistent copy of the subject name. */ - node->data.name = (WOLFSSL_X509_NAME*)XMALLOC( - sizeof(WOLFSSL_X509_NAME), NULL, DYNAMIC_TYPE_OPENSSL); - if (node->data.name == NULL) { - XFREE(node, NULL, DYNAMIC_TYPE_OPENSSL); - break; - } - XMEMCPY(node->data.name, subjectName, sizeof(WOLFSSL_X509_NAME)); - /* Clear pointers so freeing certificate doesn't free memory. */ - XMEMSET(subjectName, 0, sizeof(WOLFSSL_X509_NAME)); + node->data.name = wolfSSL_X509_NAME_dup(subjectName); /* Put node on the front of the list. */ node->num = (list == NULL) ? 1 : list->num + 1; @@ -13629,6 +13925,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) WOLFSSL_ENTER("BIO_f_buffer"); meth.type = WOLFSSL_BIO_BUFFER; + meth.custom = NULL; return &meth; } @@ -13648,8 +13945,9 @@ int wolfSSL_set_compression(WOLFSSL* ssl) { static WOLFSSL_BIO_METHOD bio_meth; - WOLFSSL_ENTER("wolfSSL_BIO_f_bio"); + WOLFSSL_ENTER("wolfSSL_BIO_s_bio"); bio_meth.type = WOLFSSL_BIO_BIO; + bio_meth.custom = NULL; return &bio_meth; } @@ -13660,8 +13958,9 @@ int wolfSSL_set_compression(WOLFSSL* ssl) { static WOLFSSL_BIO_METHOD file_meth; - WOLFSSL_ENTER("wolfSSL_BIO_f_file"); + WOLFSSL_ENTER("wolfSSL_BIO_s_file"); file_meth.type = WOLFSSL_BIO_FILE; + file_meth.custom = NULL; return &file_meth; } @@ -13672,8 +13971,9 @@ int wolfSSL_set_compression(WOLFSSL* ssl) { static WOLFSSL_BIO_METHOD meth; - WOLFSSL_ENTER("BIO_f_ssl"); + WOLFSSL_ENTER("wolfSSL_BIO_f_ssl"); meth.type = WOLFSSL_BIO_SSL; + meth.custom = NULL; return &meth; } @@ -13683,7 +13983,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) { static WOLFSSL_BIO_METHOD meth; - WOLFSSL_ENTER("BIO_s_socket"); + WOLFSSL_ENTER("wolfSSL_BIO_s_socket"); meth.type = WOLFSSL_BIO_SOCKET; return &meth; @@ -13743,11 +14043,19 @@ int wolfSSL_set_compression(WOLFSSL* ssl) WOLFSSL_BIO* wolfSSL_BIO_new(WOLFSSL_BIO_METHOD* method) { - WOLFSSL_BIO* bio = (WOLFSSL_BIO*) XMALLOC(sizeof(WOLFSSL_BIO), 0, - DYNAMIC_TYPE_OPENSSL); + WOLFSSL_BIO* bio; + WOLFSSL_ENTER("wolfSSL_BIO_new"); + if (method == NULL) { + WOLFSSL_MSG("Bad method pointer passed in"); + return NULL; + } + + bio = (WOLFSSL_BIO*) XMALLOC(sizeof(WOLFSSL_BIO), 0, + DYNAMIC_TYPE_OPENSSL); if (bio) { XMEMSET(bio, 0, sizeof(WOLFSSL_BIO)); + bio->method = method; bio->type = method->type; bio->close = BIO_CLOSE; /* default to close things */ if (method->type != WOLFSSL_BIO_FILE && @@ -13761,6 +14069,11 @@ int wolfSSL_set_compression(WOLFSSL* ssl) } bio->mem_buf->data = (char*)bio->mem; } + + /* check if is custom method */ + if (method->custom) { + method->custom->createCb(bio); + } } return bio; } @@ -13811,12 +14124,29 @@ int wolfSSL_set_compression(WOLFSSL* ssl) /* * Note : If the flag BIO_NOCLOSE is set then freeing memory buffers is up * to the application. + * Returns 1 on success, 0 on failure */ int wolfSSL_BIO_free(WOLFSSL_BIO* bio) { + int ret; + /* unchain?, doesn't matter in goahead since from free all */ WOLFSSL_ENTER("wolfSSL_BIO_free"); if (bio) { + + if (bio->infoCb) { + /* info callback is called before free */ + ret = (int)bio->infoCb(bio, WOLFSSL_BIO_CB_FREE, NULL, 0, 0, 1); + if (ret <= 0) { + return ret; + } + } + + /* call custom set free callback */ + if (bio->method->custom && bio->method->custom->freeCb) { + bio->method->custom->freeCb(bio); + } + /* remove from pair by setting the paired bios pair to NULL */ if (bio->pair != NULL) { bio->pair->pair = NULL; @@ -13860,7 +14190,13 @@ int wolfSSL_set_compression(WOLFSSL* ssl) XFREE(bio, 0, DYNAMIC_TYPE_OPENSSL); } - return 0; + return 1; + } + + /* like BIO_free, but no return value */ + void wolfSSL_BIO_vfree(WOLFSSL_BIO* bio) + { + wolfSSL_BIO_free(bio); } @@ -14057,6 +14393,36 @@ int wolfSSL_set_compression(WOLFSSL* ssl) #endif } +#if (defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE)) + /* print out and clear all errors */ + void wolfSSL_ERR_print_errors(WOLFSSL_BIO* bio) + { + const char* file = NULL; + const char* reason = NULL; + int ret; + int line = 0; + char buf[WOLFSSL_MAX_ERROR_SZ * 2]; + + WOLFSSL_ENTER("wolfSSL_ERR_print_errors"); + + if (bio == NULL) { + WOLFSSL_MSG("BIO passed in was null"); + return; + } + + do { + ret = wc_PeekErrorNode(0, &file, &reason, &line); + if (ret >= 0) { + const char* r = wolfSSL_ERR_reason_error_string(ret - ret - ret); + XSNPRINTF(buf, sizeof(buf), "error:%d:wolfSSL library:%s:%s:%d\n", + ret, r, file, line); + wolfSSL_BIO_write(bio, buf, (int)XSTRLEN(buf)); + wc_RemoveErrorNode(0); + } + } while (ret >= 0); + } +#endif /* OPENSSL_EXTRA || DEBUG_WOLFSSL_VERBOSE */ + #endif /* OPENSSL_EXTRA || HAVE_WEBSERVER */ @@ -14092,7 +14458,125 @@ size_t wolfSSL_get_server_random(const WOLFSSL *ssl, unsigned char *out, XMEMCPY(out, ssl->arrays->serverRandom, size); return size; } -#endif /* !defined(NO_WOLFSSL_SERVER) */ + + +/* Used to get the peer ephemeral public key sent during the connection + * NOTE: currently wolfSSL_KeepHandshakeResources(WOLFSSL* ssl) must be called + * before the ephemeral key is stored. + * return WOLFSSL_SUCCESS on success */ +int wolfSSL_get_server_tmp_key(const WOLFSSL* ssl, WOLFSSL_EVP_PKEY** pkey) +{ + WOLFSSL_EVP_PKEY* ret = NULL; + + WOLFSSL_ENTER("wolfSSL_get_server_tmp_key"); + + if (ssl == NULL || pkey == NULL) { + WOLFSSL_MSG("Bad argument passed in"); + return WOLFSSL_FAILURE; + } + +#ifdef HAVE_ECC + if (ssl->peerEccKey != NULL) { + unsigned char* der; + unsigned char* pt; + unsigned int derSz = 0; + int sz; + + if (wc_ecc_export_x963(ssl->peerEccKey, NULL, &derSz) != + LENGTH_ONLY_E) { + WOLFSSL_MSG("get ecc der size failed"); + return WOLFSSL_FAILURE; + } + + derSz += MAX_SEQ_SZ + (2 * MAX_ALGO_SZ) + MAX_SEQ_SZ + TRAILING_ZERO; + der = (unsigned char*)XMALLOC(derSz, ssl->heap, DYNAMIC_TYPE_KEY); + if (der == NULL) { + WOLFSSL_MSG("Memory error"); + return WOLFSSL_FAILURE; + } + + if ((sz = wc_EccPublicKeyToDer(ssl->peerEccKey, der, derSz, 1)) <= 0) { + WOLFSSL_MSG("get ecc der failed"); + XFREE(der, ssl->heap, DYNAMIC_TYPE_KEY); + return WOLFSSL_FAILURE; + } + pt = der; /* in case pointer gets advanced */ + ret = wolfSSL_d2i_PUBKEY(NULL, &pt, sz); + XFREE(der, ssl->heap, DYNAMIC_TYPE_KEY); + } +#endif + + *pkey = ret; + if (ret == NULL) + return WOLFSSL_FAILURE; + else + return WOLFSSL_SUCCESS; +} + +#endif /* !NO_WOLFSSL_SERVER */ + +int wolfSSL_CTX_set_min_proto_version(WOLFSSL_CTX* ctx, int version) +{ + WOLFSSL_ENTER("wolfSSL_CTX_set_min_proto_version"); + + if (ctx == NULL) { + return BAD_FUNC_ARG; + } + + switch (version) { +#if defined(WOLFSSL_ALLOW_SSLV3) && !defined(NO_OLD_TLS) + case SSL3_VERSION: + ctx->minDowngrade = SSLv3_MINOR; + break; +#endif +#ifndef NO_TLS + #ifndef NO_OLD_TLS + #ifdef WOLFSSL_ALLOW_TLSV10 + case TLS1_VERSION: + ctx->minDowngrade = TLSv1_MINOR; + break; + #endif + case TLS1_1_VERSION: + ctx->minDowngrade = TLSv1_1_MINOR; + break; + #endif + #ifndef WOLFSSL_NO_TLS12 + case TLS1_2_VERSION: + ctx->minDowngrade = TLSv1_2_MINOR; + break; + #endif + #ifdef WOLFSSL_TLS13 + case TLS1_3_VERSION: + ctx->minDowngrade = TLSv1_3_MINOR; + break; + #endif +#endif +#ifdef WOLFSSL_DTLS + #ifndef NO_OLD_TLS + case DTLS1_VERSION: + ctx->minDowngrade = DTLS_MINOR; + break; + #endif + case DTLS1_2_VERSION: + ctx->minDowngrade = DTLSv1_2_MINOR; + break; +#endif + default: + return BAD_FUNC_ARG; + } + + return WOLFSSL_SUCCESS; +} + +int wolfSSL_CTX_set_max_proto_version(WOLFSSL_CTX* ctx, int ver) +{ + WOLFSSL_ENTER("wolfSSL_CTX_set_max_proto_version"); + + /* supported only at compile-time only */ + (void)ctx; + (void)ver; + return WOLFSSL_SUCCESS; +} #if !defined(NO_WOLFSSL_CLIENT) @@ -14527,6 +15011,7 @@ const WOLFSSL_EVP_MD *wolfSSL_EVP_get_digestbyname(const char *name) const struct alias *al; const struct s_ent *ent; + for (al = alias_tbl; al->name != NULL; al++) if(XSTRNCMP(name, al->alias, XSTRLEN(al->alias)+1) == 0) { name = al->name; @@ -16652,7 +17137,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) int wolfSSL_set_session_id_context(WOLFSSL* ssl, const unsigned char* id, unsigned int len) { - WOLFSSL_STUB("wolfSSL_set_session_id_context"); + WOLFSSL_ENTER("wolfSSL_set_session_id_context"); if (len > ID_LEN || ssl == NULL || id == NULL) { return SSL_FAILURE; @@ -16704,7 +17189,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } -#ifdef DEBUG_WOLFSSL +#if defined(DEBUG_WOLFSSL) || defined(OPENSSL_EXTRA) static const char WOLFSSL_SYS_ACCEPT_T[] = "accept"; static const char WOLFSSL_SYS_BIND_T[] = "bind"; static const char WOLFSSL_SYS_CONNECT_T[] = "connect"; @@ -16755,12 +17240,17 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) { WOLFSSL_ENTER("wolfSSL_ERR_put_error"); - #ifndef DEBUG_WOLFSSL + #if !defined(DEBUG_WOLFSSL) && !defined(OPENSSL_EXTRA) (void)fun; (void)err; (void)file; (void)line; WOLFSSL_MSG("Not compiled in debug mode"); + #elif defined(OPENSSL_EXTRA) && defined(_WIN32) + (void)fun; + (void)file; + (void)line; + WOLFSSL_ERROR(err); #else WOLFSSL_ERROR_LINE(err, wolfSSL_ERR_sys_func(fun), (unsigned int)line, file, NULL); @@ -16893,11 +17383,28 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) * don't */ static void ExternalFreeX509(WOLFSSL_X509* x509) { + int doFree = 0; + WOLFSSL_ENTER("ExternalFreeX509"); if (x509) { if (x509->dynamicMemory) { - FreeX509(x509); - XFREE(x509, x509->heap, DYNAMIC_TYPE_X509); + #if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL) + if (wc_LockMutex(&x509->refMutex) != 0) { + WOLFSSL_MSG("Couldn't lock x509 mutex"); + } + /* only free if all references to it are done */ + x509->refCount--; + if (x509->refCount == 0) + doFree = 1; + wc_UnLockMutex(&x509->refMutex); + #else + doFree = 1; + #endif /* OPENSSL_EXTRA */ + + if (doFree) { + FreeX509(x509); + XFREE(x509, x509->heap, DYNAMIC_TYPE_X509); + } } else { WOLFSSL_MSG("free called on non dynamic object, not freeing"); } @@ -17227,7 +17734,7 @@ WOLFSSL_X509* wolfSSL_X509_d2i(WOLFSSL_X509** x509, const byte* in, int len) if (x509 == NULL) return NULL; - return x509->notBefore; + return x509->notBefore.data; } @@ -17238,7 +17745,7 @@ WOLFSSL_X509* wolfSSL_X509_d2i(WOLFSSL_X509** x509, const byte* in, int len) if (x509 == NULL) return NULL; - return x509->notAfter; + return x509->notAfter.data; } @@ -17335,6 +17842,30 @@ byte* wolfSSL_X509_get_hw_serial_number(WOLFSSL_X509* x509,byte* in, /* require OPENSSL_EXTRA since wolfSSL_X509_free is wrapped by OPENSSL_EXTRA */ #if !defined(NO_CERTS) && defined(OPENSSL_EXTRA) + + +WOLFSSL_ASN1_TIME* wolfSSL_X509_get_notBefore(WOLFSSL_X509* x509) +{ + WOLFSSL_ENTER("wolfSSL_X509_get_notBefore"); + + if (x509 == NULL) + return NULL; + + return &(x509->notBefore); +} + + +WOLFSSL_ASN1_TIME* wolfSSL_X509_get_notAfter(WOLFSSL_X509* x509) +{ + WOLFSSL_ENTER("wolfSSL_X509_get_notAfter"); + + if (x509 == NULL) + return NULL; + + return &(x509->notAfter); +} + + /* return 1 on success 0 on fail */ int wolfSSL_sk_X509_push(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, WOLFSSL_X509* x509) { @@ -17398,28 +17929,6 @@ WOLFSSL_X509* wolfSSL_sk_X509_pop(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk) { return x509; } - -/* Getter function for WOLFSSL_X509_NAME pointer - * - * sk is the stack to retrieve pointer from - * i is the index value in stack - * - * returns a pointer to a WOLFSSL_X509_NAME structure on success and NULL on - * fail - */ -void* wolfSSL_sk_X509_NAME_value(const STACK_OF(WOLFSSL_X509_NAME)* sk, int i) -{ - WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_value"); - - for (; sk != NULL && i > 0; i--) - sk = sk->next; - - if (i != 0 || sk == NULL) - return NULL; - return sk->data.name; -} - - /* Getter function for WOLFSSL_X509 pointer * * sk is the stack to retrieve pointer from @@ -17440,6 +17949,11 @@ void* wolfSSL_sk_X509_value(STACK_OF(WOLFSSL_X509)* sk, int i) return sk->data.x509; } +void* wolfSSL_sk_X509_shift(WOLF_STACK_OF(WOLFSSL_X509)* sk) +{ + return wolfSSL_sk_X509_pop(sk); +} + /* Free's all nodes in X509 stack. This is different then wolfSSL_sk_X509_free * in that it allows for choosing the function to use when freeing an X509s. @@ -17476,7 +17990,7 @@ void wolfSSL_sk_X509_pop_free(STACK_OF(WOLFSSL_X509)* sk, void f (WOLFSSL_X509*) /* free structure for x509 stack */ -void wolfSSL_sk_X509_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk) { +void wolfSSL_sk_X509_free(WOLF_STACK_OF(WOLFSSL_X509)* sk) { WOLFSSL_STACK* node; if (sk == NULL) { @@ -17503,6 +18017,7 @@ void wolfSSL_sk_X509_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk) { XFREE(sk, NULL, DYNAMIC_TYPE_X509); } + #endif /* NO_CERTS && OPENSSL_EXTRA */ #if defined(OPENSSL_ALL) || defined (WOLFSSL_QT) @@ -17594,6 +18109,110 @@ void wolfSSL_sk_ACCESS_DESCRIPTION_pop_free(WOLFSSL_STACK* sk, #ifdef OPENSSL_EXTRA +/* create a generic wolfSSL stack node + * returns a new WOLFSSL_STACK structure on success */ +WOLFSSL_STACK* wolfSSL_sk_new_node(void* heap) +{ + WOLFSSL_STACK* sk = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), heap, + DYNAMIC_TYPE_OPENSSL); + if (sk != NULL) { + XMEMSET(sk, 0, sizeof(*sk)); + sk->heap = heap; + } + + return sk; +} + + +/* free's node but does not free internal data such as in->data.x509 */ +void wolfSSL_sk_free_node(WOLFSSL_STACK* in) +{ + if (in != NULL) { + XFREE(in, in->heap, DYNAMIC_TYPE_OPENSSL); + } +} + + +/* pushes node "in" onto "stack" and returns pointer to the new stack on success + * also handles internal "num" for number of nodes on stack + * return WOLFSSL_SUCCESS on success + */ +int wolfSSL_sk_push_node(WOLFSSL_STACK** stack, WOLFSSL_STACK* in) +{ + if (stack == NULL || in == NULL) { + return WOLFSSL_FAILURE; + } + + if (*stack == NULL) { + in->num = 1; + *stack = in; + return WOLFSSL_SUCCESS; + } + + in->num = (*stack)->num + 1; + in->next = *stack; + *stack = in; + return WOLFSSL_SUCCESS; +} + +/* Creates and returns new GENERAL_NAME structure */ +WOLFSSL_GENERAL_NAME* wolfSSL_GENERAL_NAME_new(void) { + WOLFSSL_GENERAL_NAME* gn; + WOLFSSL_ENTER("GENERAL_NAME_new"); + + gn = (WOLFSSL_GENERAL_NAME*)XMALLOC(sizeof(WOLFSSL_GENERAL_NAME), NULL, + DYNAMIC_TYPE_ASN1); + if (gn == NULL) { + return NULL; + } + XMEMSET(gn, 0, sizeof(WOLFSSL_GENERAL_NAME)); + + gn->d.ia5 = wolfSSL_ASN1_STRING_new(); + if (gn->d.ia5 == NULL) { + WOLFSSL_MSG("Issue creating ASN1_STRING struct"); + wolfSSL_GENERAL_NAME_free(gn); + return NULL; + } + return gn; +} + +/* return 1 on success 0 on fail */ +int wolfSSL_sk_GENERAL_NAME_push(WOLF_STACK_OF(WOLFSSL_GENERAL_NAME)* sk, + WOLFSSL_GENERAL_NAME* gn) +{ + WOLFSSL_STACK* node; + WOLFSSL_ENTER("wolfSSL_sk_GENERAL_NAME_push"); + + if (sk == NULL || gn == NULL) { + return WOLFSSL_FAILURE; + } + + /* no previous values in stack */ + if (sk->data.gn == NULL) { + sk->data.gn = gn; + sk->num += 1; + return WOLFSSL_SUCCESS; + } + + /* stack already has value(s) create a new node and add more */ + node = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_ASN1); + if (node == NULL) { + WOLFSSL_MSG("Memory error"); + return WOLFSSL_FAILURE; + } + XMEMSET(node, 0, sizeof(WOLFSSL_STACK)); + + /* push new obj onto head of stack */ + node->data.gn = sk->data.gn; + node->next = sk->next; + sk->next = node; + sk->data.gn = gn; + sk->num += 1; + + return WOLFSSL_SUCCESS; +} + /* Returns the general name at index i from the stack * * sk stack to get general name from @@ -17601,7 +18220,7 @@ void wolfSSL_sk_ACCESS_DESCRIPTION_pop_free(WOLFSSL_STACK* sk, * * return a pointer to the internal node of the stack */ -WOLFSSL_ASN1_OBJECT* wolfSSL_sk_GENERAL_NAME_value(WOLFSSL_STACK* sk, int i) +WOLFSSL_GENERAL_NAME* wolfSSL_sk_GENERAL_NAME_value(WOLFSSL_STACK* sk, int i) { WOLFSSL_STACK* cur; int j; @@ -17621,7 +18240,7 @@ WOLFSSL_ASN1_OBJECT* wolfSSL_sk_GENERAL_NAME_value(WOLFSSL_STACK* sk, int i) return NULL; } - return cur->data.obj; + return cur->data.gn; } @@ -17665,20 +18284,78 @@ void wolfSSL_sk_GENERAL_NAME_pop_free(WOLFSSL_STACK* sk, WOLFSSL_STACK* tmp = node; node = node->next; - wolfSSL_ASN1_OBJECT_free(tmp->data.obj); + wolfSSL_GENERAL_NAME_free(tmp->data.gn); XFREE(tmp, NULL, DYNAMIC_TYPE_ASN1); sk->num -= 1; } /* free head of stack */ if (sk->num == 1) { - wolfSSL_ASN1_OBJECT_free(sk->data.obj); + wolfSSL_GENERAL_NAME_free(sk->data.gn); } XFREE(sk, NULL, DYNAMIC_TYPE_ASN1); } + +/* returns the number of nodes in stack on success and WOLFSSL_FATAL_ERROR + * on fail */ +int wolfSSL_sk_ACCESS_DESCRIPTION_num(WOLFSSL_STACK* sk) +{ + if (sk == NULL) { + return WOLFSSL_FATAL_ERROR; + } + + return (int)sk->num; +} + +#ifndef NO_WOLFSSL_STUB +/* similar to call to sk_ACCESS_DESCRIPTION_pop_free */ +void wolfSSL_AUTHORITY_INFO_ACCESS_free( + WOLF_STACK_OF(WOLFSSL_ACCESS_DESCRIPTION)* sk) +{ + WOLFSSL_STUB("wolfSSL_AUTHORITY_INFO_ACCESS_free"); + (void)sk; +} +#endif + +/* returns the node at index "idx", NULL if not found */ +static WOLFSSL_STACK* wolfSSL_sk_get_node(WOLFSSL_STACK* sk, int idx) +{ + int i; + WOLFSSL_STACK* ret = NULL; + WOLFSSL_STACK* current = NULL; + + current = sk; + for (i = 0; i < idx && current != NULL; i++) { + if (i == idx) { + ret = current; + break; + } + current = current->next; + } + return ret; +} + + +/* returns NULL on fail and pointer to internal data on success */ +WOLFSSL_ACCESS_DESCRIPTION* wolfSSL_sk_ACCESS_DESCRIPTION_value( + WOLFSSL_STACK* sk, int idx) +{ + WOLFSSL_STACK* ret; + + if (sk == NULL) { + return NULL; + } + + ret = wolfSSL_sk_get_node(sk, idx); + if (ret != NULL) { + return ret->data.access; + } + return NULL; +} + /* Frees GENERAL_NAME objects. */ void wolfSSL_GENERAL_NAME_free(WOLFSSL_GENERAL_NAME* name) @@ -17687,15 +18364,23 @@ void wolfSSL_GENERAL_NAME_free(WOLFSSL_GENERAL_NAME* name) if(name != NULL) { if (name->d.dNSName != NULL) { wolfSSL_ASN1_STRING_free(name->d.dNSName); + name->d.dNSName = NULL; } if (name->d.uniformResourceIdentifier != NULL) { wolfSSL_ASN1_STRING_free(name->d.uniformResourceIdentifier); + name->d.uniformResourceIdentifier = NULL; } if (name->d.iPAddress != NULL) { wolfSSL_ASN1_STRING_free(name->d.iPAddress); + name->d.iPAddress = NULL; } if (name->d.registeredID != NULL) { wolfSSL_ASN1_OBJECT_free(name->d.registeredID); + name->d.registeredID = NULL; + } + if (name->d.ia5 != NULL) { + wolfSSL_ASN1_STRING_free(name->d.ia5); + name->d.ia5 = NULL; } XFREE(name, NULL, DYNAMIC_TYPE_OPENSSL); } @@ -17729,6 +18414,61 @@ void wolfSSL_GENERAL_NAMES_free(WOLFSSL_GENERAL_NAMES *gens) XFREE(gens, NULL, DYNAMIC_TYPE_ASN1); } +#if defined(OPENSSL_ALL) +WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* wolfSSL_sk_X509_EXTENSION_new_null(void) +{ + return (WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)*)wolfSSL_sk_new_node(NULL); +} + +/* returns the number of nodes on the stack */ +int wolfSSL_sk_X509_EXTENSION_num(WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* sk) +{ + if (sk != NULL) { + return (int)sk->num; + } + return WOLFSSL_FATAL_ERROR; +} + + +/* returns null on failure and pointer to internal value on success */ +WOLFSSL_X509_EXTENSION* wolfSSL_sk_X509_EXTENSION_value( + WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* sk, int idx) +{ + WOLFSSL_STACK* ret; + + if (sk == NULL) { + return NULL; + } + + ret = wolfSSL_sk_get_node(sk, idx); + if (ret != NULL) { + return ret->data.ext; + } + return NULL; +} + +/* frees all of the nodes and the values in stack */ +void wolfSSL_sk_X509_EXTENSION_pop_free( + WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* sk, + void f (WOLFSSL_X509_EXTENSION*)) +{ + WOLFSSL_STACK* current; + + if (sk == NULL) { + return; + } + + current = sk; + while (current != NULL) { + WOLFSSL_STACK* toFree = current; + current = current->next; + + f(toFree->data.ext); + wolfSSL_sk_free_node(toFree); + } +} +#endif /* OPENSSL_ALL */ + #endif /* OPENSSL_EXTRA */ #ifndef NO_FILESYSTEM @@ -18208,7 +18948,6 @@ char* wolfSSL_i2s_ASN1_STRING(WOLFSSL_v3_ext_method *method, const WOLFSSL_ASN1_ return tmp; } - #endif /* NO_ASN */ void wolfSSL_set_connect_state(WOLFSSL* ssl) @@ -18284,11 +19023,18 @@ void wolfSSL_SESSION_free(WOLFSSL_SESSION* session) } #endif -const char* wolfSSL_get_version(WOLFSSL* ssl) + +/* helper function that takes in a protocol version struct and returns string */ +static const char* wolfSSL_internal_get_version(ProtocolVersion* version) { - WOLFSSL_ENTER("SSL_get_version"); - if (ssl->version.major == SSLv3_MAJOR) { - switch (ssl->version.minor) { + WOLFSSL_ENTER("wolfSSL_get_version"); + + if (version == NULL) { + return "Bad arg"; + } + + if (version->major == SSLv3_MAJOR) { + switch (version->minor) { #ifndef NO_OLD_TLS #ifdef WOLFSSL_ALLOW_SSLV3 case SSLv3_MINOR : @@ -18326,8 +19072,8 @@ const char* wolfSSL_get_version(WOLFSSL* ssl) } } #ifdef WOLFSSL_DTLS - else if (ssl->version.major == DTLS_MAJOR) { - switch (ssl->version.minor) { + else if (version->major == DTLS_MAJOR) { + switch (version->minor) { case DTLS_MINOR : return "DTLS"; case DTLSv1_2_MINOR : @@ -18341,6 +19087,17 @@ const char* wolfSSL_get_version(WOLFSSL* ssl) } +const char* wolfSSL_get_version(WOLFSSL* ssl) +{ + if (ssl == NULL) { + WOLFSSL_MSG("Bad argument"); + return "unknown"; + } + + return wolfSSL_internal_get_version(&ssl->version); +} + + /* current library version */ const char* wolfSSL_lib_version(void) { @@ -18366,8 +19123,11 @@ int wolfSSL_get_current_cipher_suite(WOLFSSL* ssl) WOLFSSL_CIPHER* wolfSSL_get_current_cipher(WOLFSSL* ssl) { WOLFSSL_ENTER("SSL_get_current_cipher"); - if (ssl) + if (ssl) { + ssl->cipher.cipherSuite0 = ssl->options.cipherSuite0; + ssl->cipher.cipherSuite = ssl->options.cipherSuite; return &ssl->cipher; + } else return NULL; } @@ -18375,17 +19135,29 @@ WOLFSSL_CIPHER* wolfSSL_get_current_cipher(WOLFSSL* ssl) const char* wolfSSL_CIPHER_get_name(const WOLFSSL_CIPHER* cipher) { - WOLFSSL_ENTER("SSL_CIPHER_get_name"); + WOLFSSL_ENTER("wolfSSL_CIPHER_get_name"); + + if (cipher == NULL) { + return NULL; + } + + #if !defined(WOLFSSL_CIPHER_INTERNALNAME) && !defined(NO_ERROR_STRINGS) + return GetCipherNameIana(cipher->cipherSuite0, cipher->cipherSuite); + #else + return wolfSSL_get_cipher_name_from_suite(cipher->cipherSuite0, + cipher->cipherSuite); + #endif +} + +const char* wolfSSL_CIPHER_get_version(const WOLFSSL_CIPHER* cipher) +{ + WOLFSSL_ENTER("SSL_CIPHER_get_version"); if (cipher == NULL || cipher->ssl == NULL) { return NULL; } - #if !defined(WOLFSSL_CIPHER_INTERNALNAME) && !defined(NO_ERROR_STRINGS) - return wolfSSL_get_cipher_name_iana(cipher->ssl); - #else - return wolfSSL_get_cipher_name_internal(cipher->ssl); - #endif + return wolfSSL_get_version(cipher->ssl); } const char* wolfSSL_SESSION_CIPHER_get_name(WOLFSSL_SESSION* session) @@ -18709,11 +19481,8 @@ WOLFSSL_EVP_PKEY* wolfSSL_X509_get_pubkey(WOLFSSL_X509* x509) WOLFSSL_EVP_PKEY* key = NULL; WOLFSSL_ENTER("X509_get_pubkey"); if (x509 != NULL) { - key = (WOLFSSL_EVP_PKEY*)XMALLOC( - sizeof(WOLFSSL_EVP_PKEY), x509->heap, - DYNAMIC_TYPE_PUBLIC_KEY); + key = wolfSSL_PKEY_new_ex(x509->heap); if (key != NULL) { - XMEMSET(key, 0, sizeof(WOLFSSL_EVP_PKEY)); if (x509->pubKeyOID == RSAk) { key->type = EVP_PKEY_RSA; } @@ -19230,6 +19999,17 @@ int wolfSSL_X509_cmp(const WOLFSSL_X509 *a, const WOLFSSL_X509 *b) } } +#ifndef NO_WOLFSSL_STUB + WOLFSSL_ASN1_STRING* wolfSSL_d2i_DISPLAYTEXT(WOLFSSL_ASN1_STRING **asn, + unsigned char **in, long len) + { + WOLFSSL_STUB("d2i_DISPLAYTEXT"); + (void)asn; + (void)in; + (void)len; + return NULL; + } +#endif #ifdef XSNPRINTF /* a snprintf function needs to be available */ /* Writes the human readable form of x509 to bio. @@ -19398,9 +20178,9 @@ int wolfSSL_X509_cmp(const WOLFSSL_X509 *a, const WOLFSSL_X509 *b) (int)XSTRLEN(" Not Before: ")) <= 0) { return WOLFSSL_FAILURE; } - if (GetTimeString(x509->notBefore + 2, ASN_UTC_TIME, + if (GetTimeString(x509->notBefore.data + 2, ASN_UTC_TIME, tmp, sizeof(tmp)) != WOLFSSL_SUCCESS) { - if (GetTimeString(x509->notBefore + 2, ASN_GENERALIZED_TIME, + if (GetTimeString(x509->notBefore.data + 2, ASN_GENERALIZED_TIME, tmp, sizeof(tmp)) != WOLFSSL_SUCCESS) { WOLFSSL_MSG("Error getting not before date"); return WOLFSSL_FAILURE; @@ -19414,9 +20194,9 @@ int wolfSSL_X509_cmp(const WOLFSSL_X509 *a, const WOLFSSL_X509 *b) (int)XSTRLEN("\n Not After : ")) <= 0) { return WOLFSSL_FAILURE; } - if (GetTimeString(x509->notAfter + 2,ASN_UTC_TIME, + if (GetTimeString(x509->notAfter.data + 2,ASN_UTC_TIME, tmp, sizeof(tmp)) != WOLFSSL_SUCCESS) { - if (GetTimeString(x509->notAfter + 2,ASN_GENERALIZED_TIME, + if (GetTimeString(x509->notAfter.data + 2,ASN_GENERALIZED_TIME, tmp, sizeof(tmp)) != WOLFSSL_SUCCESS) { WOLFSSL_MSG("Error getting not before date"); return WOLFSSL_FAILURE; @@ -20267,8 +21047,9 @@ WOLFSSL_BIO_METHOD* wolfSSL_BIO_s_mem(void) { static WOLFSSL_BIO_METHOD meth; - WOLFSSL_ENTER("BIO_s_mem"); + WOLFSSL_ENTER("wolfSSL_BIO_s_mem"); meth.type = WOLFSSL_BIO_MEMORY; + meth.custom = NULL; return &meth; } @@ -20280,6 +21061,7 @@ WOLFSSL_BIO_METHOD* wolfSSL_BIO_f_base64(void) WOLFSSL_ENTER("wolfSSL_BIO_f_base64"); meth.type = WOLFSSL_BIO_BASE64; + meth.custom = NULL; return &meth; } @@ -20511,6 +21293,7 @@ WOLFSSL_X509_LOOKUP_METHOD* wolfSSL_X509_LOOKUP_file(void) WOLFSSL_X509_LOOKUP* wolfSSL_X509_STORE_add_lookup(WOLFSSL_X509_STORE* store, WOLFSSL_X509_LOOKUP_METHOD* m) { + WOLFSSL_ENTER("SSL_X509_STORE_add_lookup"); if (store == NULL) return NULL; @@ -20676,7 +21459,6 @@ WC_PKCS12* wolfSSL_d2i_PKCS12_bio(WOLFSSL_BIO* bio, WC_PKCS12** pkcs12) return localPkcs12; } - /* Converts the PKCS12 to DER format and outputs it into bio. * * bio is the structure to hold output DER @@ -20709,15 +21491,42 @@ int wolfSSL_i2d_PKCS12_bio(WOLFSSL_BIO *bio, WC_PKCS12 *pkcs12) return ret; } - -/* helper function to get DER buffer from WOLFSSL_EVP_PKEY */ -static int wolfSSL_i2d_PrivateKey(WOLFSSL_EVP_PKEY* key, unsigned char** der) +/* helper function to get raw pointer to DER buffer from WOLFSSL_EVP_PKEY */ +static int wolfSSL_EVP_PKEY_get_der(WOLFSSL_EVP_PKEY* key, unsigned char** der) { *der = (unsigned char*)key->pkey.ptr; return key->pkey_sz; } +/* Copies unencrypted DER key buffer into "der". If "der" is null then the size + * of buffer needed is returned + * NOTE: This also advances the "der" pointer to be at the end of buffer. + * + * Returns size of key buffer on success + */ +int wolfSSL_i2d_PrivateKey(WOLFSSL_EVP_PKEY* key, unsigned char** der) +{ + unsigned char* pt; + int sz; + + if (key == NULL) { + return WOLFSSL_FATAL_ERROR; + } + + sz = wolfSSL_EVP_PKEY_get_der(key, &pt); + if (sz <= 0) { + return WOLFSSL_FATAL_ERROR; + } + + if (der != NULL) { + /* since this function signature has no size value passed in it is + * assumed that the user has allocated a large enough buffer */ + XMEMCPY(*der, pt, sz); + *der += sz; + } + return sz; +} /* Creates a new WC_PKCS12 structure * @@ -20757,7 +21566,7 @@ WC_PKCS12* wolfSSL_PKCS12_create(char* pass, char* name, } passSz = (word32)XSTRLEN(pass); - if ((ret = wolfSSL_i2d_PrivateKey(pkey, &keyDer)) < 0) { + if ((ret = wolfSSL_EVP_PKEY_get_der(pkey, &keyDer)) < 0) { WOLFSSL_LEAVE("wolfSSL_PKCS12_create", ret); return NULL; } @@ -21188,7 +21997,6 @@ WOLFSSL_STACK* wolfSSL_X509_STORE_CTX_get_chain(WOLFSSL_X509_STORE_CTX* ctx) return ctx->chain; } - /* make shallow copy of the stack, data pointers are copied by reference */ WOLFSSL_STACK* wolfSSL_sk_X509_dup(WOLFSSL_STACK* sk) { @@ -21303,6 +22111,7 @@ int wolfSSL_X509_STORE_add_cert(WOLFSSL_X509_STORE* store, WOLFSSL_X509* x509) WOLFSSL_X509_STORE* wolfSSL_X509_STORE_new(void) { WOLFSSL_X509_STORE* store = NULL; + WOLFSSL_ENTER("SSL_X509_STORE_new"); if ((store = (WOLFSSL_X509_STORE*)XMALLOC(sizeof(WOLFSSL_X509_STORE), NULL, DYNAMIC_TYPE_X509_STORE)) == NULL) @@ -21402,8 +22211,10 @@ int wolfSSL_X509_STORE_get_by_subject(WOLFSSL_X509_STORE_CTX* ctx, int idx, WOLFSSL_X509_STORE_CTX* wolfSSL_X509_STORE_CTX_new(void) { - WOLFSSL_X509_STORE_CTX* ctx = (WOLFSSL_X509_STORE_CTX*)XMALLOC( - sizeof(WOLFSSL_X509_STORE_CTX), NULL, + WOLFSSL_X509_STORE_CTX* ctx; + WOLFSSL_ENTER("X509_STORE_CTX_new"); + + ctx = (WOLFSSL_X509_STORE_CTX*)XMALLOC(sizeof(WOLFSSL_X509_STORE_CTX), NULL, DYNAMIC_TYPE_X509_CTX); if (ctx != NULL) { ctx->param = NULL; @@ -21434,8 +22245,8 @@ int wolfSSL_X509_STORE_CTX_init(WOLFSSL_X509_STORE_CTX* ctx, ctx->chain = sk; ctx->domain = NULL; -#ifdef HAVE_EX_DATA - ctx->ex_data = NULL; +#if defined(HAVE_EX_DATA) || defined(FORTRESS) + XMEMSET(ctx->ex_data, 0, MAX_EX_DATA * sizeof(void*)); #endif ctx->userCtx = NULL; ctx->error = 0; @@ -21486,6 +22297,7 @@ void wolfSSL_X509_STORE_CTX_cleanup(WOLFSSL_X509_STORE_CTX* ctx) int wolfSSL_X509_verify_cert(WOLFSSL_X509_STORE_CTX* ctx) { + WOLFSSL_ENTER("wolfSSL_X509_verify_cert"); if (ctx != NULL && ctx->store != NULL && ctx->store->cm != NULL && ctx->current_cert != NULL && ctx->current_cert->derCert != NULL) { return wolfSSL_CertManagerVerifyBuffer(ctx->store->cm, @@ -21745,6 +22557,8 @@ WOLFSSL_EVP_PKEY* wolfSSL_PKEY_new_ex(void* heap) WOLFSSL_MSG("memory failure"); return NULL; } + pkey->references = 1; + wc_InitMutex(&pkey->refMutex); } else { WOLFSSL_MSG("memory failure"); @@ -21756,38 +22570,52 @@ WOLFSSL_EVP_PKEY* wolfSSL_PKEY_new_ex(void* heap) void wolfSSL_EVP_PKEY_free(WOLFSSL_EVP_PKEY* key) { + int doFree = 0; WOLFSSL_ENTER("wolfSSL_EVP_PKEY_free"); if (key != NULL) { - wc_FreeRng(&key->rng); - - if (key->pkey.ptr != NULL) { - XFREE(key->pkey.ptr, key->heap, DYNAMIC_TYPE_PUBLIC_KEY); - key->pkey.ptr = NULL; + if (wc_LockMutex(&key->refMutex) != 0) { + WOLFSSL_MSG("Couldn't lock pkey mutex"); } - switch(key->type) - { - #ifndef NO_RSA - case EVP_PKEY_RSA: - if (key->rsa != NULL && key->ownRsa == 1) { - wolfSSL_RSA_free(key->rsa); - key->rsa = NULL; - } - break; - #endif /* NO_RSA */ - #ifdef HAVE_ECC - case EVP_PKEY_EC: - if (key->ecc != NULL && key->ownEcc == 1) { - wolfSSL_EC_KEY_free(key->ecc); - key->ecc = NULL; - } - break; - #endif /* HAVE_ECC */ - - default: - break; + /* only free if all references to it are done */ + key->references--; + if (key->references == 0) { + doFree = 1; + } + wc_UnLockMutex(&key->refMutex); + + if (doFree) { + wc_FreeRng(&key->rng); + + if (key->pkey.ptr != NULL) { + XFREE(key->pkey.ptr, key->heap, DYNAMIC_TYPE_PUBLIC_KEY); + key->pkey.ptr = NULL; + } + switch(key->type) + { + #ifndef NO_RSA + case EVP_PKEY_RSA: + if (key->rsa != NULL && key->ownRsa == 1) { + wolfSSL_RSA_free(key->rsa); + key->rsa = NULL; + } + break; + #endif /* NO_RSA */ + + #ifdef HAVE_ECC + case EVP_PKEY_EC: + if (key->ecc != NULL && key->ownEcc == 1) { + wolfSSL_EC_KEY_free(key->ecc); + key->ecc = NULL; + } + break; + #endif /* HAVE_ECC */ + + default: + break; + } + XFREE(key, key->heap, DYNAMIC_TYPE_PUBLIC_KEY); } - XFREE(key, key->heap, DYNAMIC_TYPE_PUBLIC_KEY); } } #endif /* OPENSSL_EXTRA_X509_SMALL */ @@ -21795,6 +22623,21 @@ void wolfSSL_EVP_PKEY_free(WOLFSSL_EVP_PKEY* key) #ifdef OPENSSL_EXTRA +/* Gets pointer to X509_STORE that was used to create context. + * + * Return valid pointer on success, NULL if ctx was NULL or not initialized + */ +WOLFSSL_X509_STORE* wolfSSL_X509_STORE_CTX_get0_store( + WOLFSSL_X509_STORE_CTX* ctx) +{ + WOLFSSL_ENTER("wolfSSL_X509_STORE_CTX_get0_store"); + + if (ctx == NULL) + return NULL; + + return ctx->store; +} + void wolfSSL_X509_STORE_CTX_set_time(WOLFSSL_X509_STORE_CTX* ctx, unsigned long flags, time_t t) @@ -22207,7 +23050,7 @@ char* wolfSSL_ASN1_TIME_to_string(WOLFSSL_ASN1_TIME* t, char* buf, int len) { int format; int dateLen; - byte* date = (byte*)t; + byte* date; WOLFSSL_ENTER("wolfSSL_ASN1_TIME_to_string"); @@ -22216,6 +23059,7 @@ char* wolfSSL_ASN1_TIME_to_string(WOLFSSL_ASN1_TIME* t, char* buf, int len) return NULL; } + date = t->data; format = *date; date++; dateLen = *date; date++; if (dateLen > len) { @@ -22246,6 +23090,7 @@ WOLFSSL_ASN1_TIME* wolfSSL_ASN1_TIME_adj(WOLFSSL_ASN1_TIME *s, time_t t, struct tm* tmpTime = NULL; time_t t_adj = 0; time_t offset_day_sec = 0; + int sz = 0; #if defined(NEED_TMP_TIME) struct tm tmpTimeStorage; @@ -22262,6 +23107,7 @@ WOLFSSL_ASN1_TIME* wolfSSL_ASN1_TIME_adj(WOLFSSL_ASN1_TIME *s, time_t t, if (s == NULL){ return NULL; } + XMEMSET(s, 0, sizeof(WOLFSSL_ASN1_TIME)); } /* compute GMT time with offset */ @@ -22298,6 +23144,7 @@ WOLFSSL_ASN1_TIME* wolfSSL_ASN1_TIME_adj(WOLFSSL_ASN1_TIME *s, time_t t, *data_ptr = (byte) ASN_UTC_TIME; data_ptr++; *data_ptr = (byte) ASN_UTC_TIME_SIZE; data_ptr++; XMEMCPY(data_ptr,(byte *)utc_str, ASN_UTC_TIME_SIZE); + sz = ASN_UTC_TIME_SIZE; /* GeneralizedTime */ } else { char gt_str[ASN_GENERALIZED_TIME_MAX]; @@ -22317,8 +23164,11 @@ WOLFSSL_ASN1_TIME* wolfSSL_ASN1_TIME_adj(WOLFSSL_ASN1_TIME *s, time_t t, *data_ptr = (byte) ASN_GENERALIZED_TIME; data_ptr++; *data_ptr = (byte) ASN_GENERALIZED_TIME_SIZE; data_ptr++; XMEMCPY(data_ptr,(byte *)gt_str, ASN_GENERALIZED_TIME_SIZE); + sz = ASN_GENERALIZED_TIME_SIZE; } + /* +2 for tag and length */ + s->length = sz + 2; return s; } #endif /* !NO_ASN_TIME && !USER_TIME && !TIME_OVERRIDES && !NO_FILESYSTEM */ @@ -22343,17 +23193,70 @@ long wolfSSL_ASN1_INTEGER_get(const WOLFSSL_ASN1_INTEGER* i) } #endif +/* get X509_STORE_CTX ex_data, max idx is MAX_EX_DATA */ void* wolfSSL_X509_STORE_CTX_get_ex_data(WOLFSSL_X509_STORE_CTX* ctx, int idx) { WOLFSSL_ENTER("wolfSSL_X509_STORE_CTX_get_ex_data"); -#if defined(HAVE_EX_DATA) || defined(FORTRESS) - if (ctx != NULL && idx == 0) - return ctx->ex_data; -#else + #if defined(HAVE_EX_DATA) || defined(FORTRESS) + if (ctx != NULL && idx < MAX_EX_DATA && idx >= 0) { + return ctx->ex_data[idx]; + } + #else (void)ctx; (void)idx; + #endif + return NULL; +} + + +/* set X509_STORE_CTX ex_data, max idx is MAX_EX_DATA. Return WOLFSSL_SUCCESS + * on success, WOLFSSL_FAILURE on error. */ +int wolfSSL_X509_STORE_CTX_set_ex_data(WOLFSSL_X509_STORE_CTX* ctx, int idx, + void *data) +{ + WOLFSSL_ENTER("wolfSSL_X509_STORE_CTX_set_ex_data"); + #if defined(HAVE_EX_DATA) || defined(FORTRESS) + if (ctx != NULL && idx < MAX_EX_DATA) + { + ctx->ex_data[idx] = data; + return WOLFSSL_SUCCESS; + } + #else + (void)ctx; + (void)idx; + (void)data; + #endif + return WOLFSSL_FAILURE; +} + +#if defined(WOLFSSL_APACHE_HTTPD) || defined(OPENSSL_ALL) +void wolfSSL_X509_STORE_CTX_set_depth(WOLFSSL_X509_STORE_CTX* ctx, int depth) +{ + WOLFSSL_ENTER("wolfSSL_X509_STORE_CTX_set_depth"); + if (ctx) + ctx->depth = depth; +} #endif - return 0; + + +WOLFSSL_X509* wolfSSL_X509_STORE_CTX_get0_current_issuer( + WOLFSSL_X509_STORE_CTX* ctx) +{ + int ret; + WOLFSSL_X509* issuer; + + WOLFSSL_ENTER("wolfSSL_X509_STORE_CTX_get0_current_issuer"); + + if (ctx == NULL) { + return NULL; + } + + ret = wolfSSL_X509_STORE_CTX_get1_issuer(&issuer, ctx, ctx->current_cert); + if (ret == WOLFSSL_SUCCESS) { + return issuer; + } + + return NULL; } @@ -22452,7 +23355,7 @@ int wolfSSL_ERR_GET_REASON(unsigned long err) */ const char* wolfSSL_alert_type_string_long(int alertID) { - WOLFSSL_ENTER("wolfSSL_aalert_type_string_long"); + WOLFSSL_ENTER("wolfSSL_alert_type_string_long"); switch (alertID) { case close_notify: @@ -23136,9 +24039,11 @@ static long wolf_set_options(long old_op, long op) WOLFSSL_MSG("\tWOLFSSL_OP_NO_SSLv2 : wolfSSL does not support SSLv2"); } +#ifdef SSL_OP_NO_TLSv1_3 if ((op & SSL_OP_NO_TLSv1_3) == SSL_OP_NO_TLSv1_3) { WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_3"); } +#endif if ((op & SSL_OP_NO_TLSv1_2) == SSL_OP_NO_TLSv1_2) { WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_2"); @@ -23183,10 +24088,12 @@ long wolfSSL_set_options(WOLFSSL* ssl, long op) ssl->options.mask = wolf_set_options(ssl->options.mask, op); +#ifdef SSL_OP_NO_TLSv1_3 if ((ssl->options.mask & SSL_OP_NO_TLSv1_3) == SSL_OP_NO_TLSv1_3) { if (ssl->version.minor == TLSv1_3_MINOR) ssl->version.minor = TLSv1_2_MINOR; } +#endif if ((ssl->options.mask & SSL_OP_NO_TLSv1_2) == SSL_OP_NO_TLSv1_2) { if (ssl->version.minor == TLSv1_2_MINOR) @@ -23246,25 +24153,43 @@ long wolfSSL_clear_options(WOLFSSL* ssl, long opt) return ssl->options.mask; } -/*** TBD ***/ -#ifndef NO_WOLFSSL_STUB -WOLFSSL_API long wolfSSL_clear_num_renegotiations(WOLFSSL *s) -{ - (void)s; - WOLFSSL_STUB("SSL_clear_num_renegotiations"); - return 0; -} -#endif -/*** TBD ***/ -#ifndef NO_WOLFSSL_STUB -WOLFSSL_API long wolfSSL_total_renegotiations(WOLFSSL *s) +#if defined(HAVE_SECURE_RENEGOTIATION) \ + || defined(HAVE_SERVER_RENEGOTIATION_INFO) +/* clears the counter for number of renegotiations done + * returns the current count before it is cleared */ +long wolfSSL_clear_num_renegotiations(WOLFSSL *s) { - (void)s; - WOLFSSL_STUB("SSL_total_renegotiations"); - return 0; + long total; + + WOLFSSL_ENTER("wolfSSL_clear_num_renegotiations"); + if (s == NULL) + return 0; + + total = s->secure_rene_count; + s->secure_rene_count = 0; + return total; } -#endif + + +/* return the number of renegotiations since wolfSSL_new */ +long wolfSSL_total_renegotiations(WOLFSSL *s) +{ + WOLFSSL_ENTER("wolfSSL_total_renegotiations"); + return wolfSSL_num_renegotiations(s); +} + + +/* return the number of renegotiations since wolfSSL_new */ +long wolfSSL_num_renegotiations(WOLFSSL* s) +{ + if (s == NULL) { + return 0; + } + + return s->secure_rene_count; +} +#endif /* HAVE_SECURE_RENEGOTIATION || HAVE_SERVER_RENEGOTIATION_INFO */ #ifndef NO_DH long wolfSSL_set_tmp_dh(WOLFSSL *ssl, WOLFSSL_DH *dh) @@ -23430,51 +24355,84 @@ WOLFSSL_API int SSL_SESSION_set1_id_context(WOLFSSL_SESSION *s, const unsigned c } #endif -#ifndef NO_WOLFSSL_STUB -/*** TBD ***/ -WOLFSSL_API void *X509_get0_tbs_sigalg(const WOLFSSL_X509 *x) +#if defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD) +/* Returns X509_ALGOR struct with signature algorithm */ +const WOLFSSL_X509_ALGOR* wolfSSL_X509_get0_tbs_sigalg(const WOLFSSL_X509 *x509) { - (void)x; - WOLFSSL_STUB("X509_get0_tbs_sigalg"); - return NULL; -} -#endif + WOLFSSL_ENTER("X509_get0_tbs_sigalg"); -#ifndef NO_WOLFSSL_STUB -/*** TBD ***/ -WOLFSSL_API void X509_ALGOR_get0(WOLFSSL_ASN1_OBJECT **paobj, int *pptype, const void **ppval, const void *algor) + if (x509 == NULL) { + WOLFSSL_MSG("x509 struct NULL error"); + return NULL; + } + + return &x509->algor; +} + +/* Sets paobj pointer to X509_ALGOR signature algorithm */ +void wolfSSL_X509_ALGOR_get0(WOLFSSL_ASN1_OBJECT **paobj, int *pptype, + const void **ppval, const WOLFSSL_X509_ALGOR *algor) { - (void)paobj; (void)pptype; (void)ppval; - (void)algor; - WOLFSSL_STUB("X509_ALGOR_get0"); -} -#endif + WOLFSSL_ENTER("X509_ALGOR_get0"); -#ifndef NO_WOLFSSL_STUB -/*** TBD ***/ -WOLFSSL_API void *X509_get_X509_PUBKEY(void * x) -{ - (void)x; - WOLFSSL_STUB("X509_get_X509_PUBKEY"); - return NULL; + if (paobj && algor) { + *paobj = algor->algorithm; + } + else { + WOLFSSL_MSG("ASN1_OBJECT NULL error"); + } } -#endif -#ifndef NO_WOLFSSL_STUB -/*** TBD ***/ -WOLFSSL_API int X509_PUBKEY_get0_param(WOLFSSL_ASN1_OBJECT **ppkalg, const unsigned char **pk, int *ppklen, void **pa, WOLFSSL_EVP_PKEY *pub) +/* Returns X509_PUBKEY structure containing X509_ALGOR and EVP_PKEY */ +WOLFSSL_X509_PUBKEY* wolfSSL_X509_get_X509_PUBKEY(const WOLFSSL_X509* x509) +{ + WOLFSSL_ENTER("X509_get_X509_PUBKEY"); + + if (x509 == NULL) { + WOLFSSL_MSG("x509 struct NULL error"); + return NULL; + } + + return (WOLFSSL_X509_PUBKEY*)&x509->key; +} + +/* Sets ppkalg pointer to X509_PUBKEY algorithm. Returns WOLFSSL_SUCCESS on + success or WOLFSSL_FAILURE on error. */ +int wolfSSL_X509_PUBKEY_get0_param(WOLFSSL_ASN1_OBJECT **ppkalg, + const unsigned char **pk, int *ppklen, void **pa, WOLFSSL_X509_PUBKEY *pub) { - (void)ppkalg; (void)pk; (void)ppklen; (void)pa; - (void)pub; - WOLFSSL_STUB("X509_PUBKEY_get0_param"); - return WOLFSSL_FAILURE; + WOLFSSL_ASN1_OBJECT* obj; + WOLFSSL_ENTER("X509_PUBKEY_get0_param"); + + if (ppkalg == NULL || pub == NULL) { + return WOLFSSL_FAILURE; + } + + if (pub->algor == NULL) { + pub->algor = (WOLFSSL_X509_ALGOR*)XMALLOC(sizeof(WOLFSSL_X509_ALGOR), + NULL, DYNAMIC_TYPE_OPENSSL); + if (pub->algor == NULL) { + return WOLFSSL_FAILURE; + } + } + obj = wolfSSL_OBJ_nid2obj(pub->pubKeyOID); + if (obj == NULL) { + WOLFSSL_MSG("Failed to create object from NID"); + return WOLFSSL_FAILURE; + } + + pub->algor->algorithm = obj; + *ppkalg = pub->algor->algorithm; + + return WOLFSSL_SUCCESS; + } -#endif +#endif /* OPENSSL_ALL || WOLFSSL_APACHE_HTTPD */ #ifndef NO_WOLFSSL_STUB /*** TBD ***/ @@ -23585,15 +24543,15 @@ WOLFSSL_API WOLF_STACK_OF(SSL_COMP) *SSL_COMP_get_compression_methods(void) } #endif -#ifndef NO_WOLFSSL_STUB -/*** TBD ***/ -WOLFSSL_API int wolfSSL_sk_SSL_CIPHER_num(const void * p) + +int wolfSSL_sk_SSL_CIPHER_num(const WOLF_STACK_OF(WOLFSSL_CIPHER)* p) { - (void)p; - WOLFSSL_STUB("wolfSSL_sk_SSL_CIPHER_num"); - return -1; + WOLFSSL_ENTER("wolfSSL_sk_SSL_CIPHER_num"); + if (p == NULL) { + return WOLFSSL_FATAL_ERROR; + } + return (int)p->num; } -#endif #if !defined(NO_FILESYSTEM) #ifndef NO_WOLFSSL_STUB @@ -23610,15 +24568,105 @@ WOLFSSL_API WOLFSSL_EVP_PKEY *wolfSSL_PEM_read_PrivateKey(XFILE fp, WOLFSSL_EVP_ #endif #endif -#ifndef NO_WOLFSSL_STUB -/*** TBD ***/ -WOLFSSL_API int X509_STORE_load_locations(WOLFSSL_X509_STORE *ctx, const char *file, const char *dir) +#if !defined(NO_FILESYSTEM) +/* Loads certificate(s) files in pem format into X509_STORE struct from either + * a file or directory. + * Returns WOLFSSL_SUCCESS on success or WOLFSSL_FAILURE if an error occurs. + */ +WOLFSSL_API int wolfSSL_X509_STORE_load_locations(WOLFSSL_X509_STORE *str, + const char *file, const char *dir) { - (void)ctx; - (void)file; - (void)dir; - WOLFSSL_STUB("X509_STORE_load_locations"); - return WOLFSSL_FAILURE; + WOLFSSL_CTX* ctx; + char *name = NULL; + int ret = WOLFSSL_SUCCESS; + int successes = 0; +#ifdef WOLFSSL_SMALL_STACK + ReadDirCtx* readCtx = NULL; +#else + ReadDirCtx readCtx[1]; +#endif + + WOLFSSL_ENTER("X509_STORE_load_locations"); + + if (str == NULL || str->cm == NULL || (file == NULL && dir == NULL)) + return WOLFSSL_FAILURE; + + /* tmp ctx for setting our cert manager */ + ctx = wolfSSL_CTX_new(cm_pick_method()); + if (ctx == NULL) + return WOLFSSL_FAILURE; + + wolfSSL_CertManagerFree(ctx->cm); + ctx->cm = str->cm; + +#ifdef HAVE_CRL + if (str->cm->crl == NULL) { + if (wolfSSL_CertManagerEnableCRL(str->cm, 0) != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Enable CRL failed"); + wolfSSL_CTX_free(ctx); + return WOLFSSL_FAILURE; + } + } +#endif + + /* Load individual file */ + if (file) { + /* Try to process file with type DETECT_CERT_TYPE to parse the + correct certificate header and footer type */ + ret = ProcessFile(ctx, file, WOLFSSL_FILETYPE_PEM, DETECT_CERT_TYPE, + NULL, 0, str->cm->crl, 0); + if (ret != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Failed to load file"); + ret = WOLFSSL_FAILURE; + } + } + + /* Load files in dir */ + if (dir && ret == WOLFSSL_SUCCESS) { + #ifdef WOLFSSL_SMALL_STACK + readCtx = (ReadDirCtx*)XMALLOC(sizeof(ReadDirCtx), ctx->heap, + DYNAMIC_TYPE_TMP_BUFFER); + if (readCtx == NULL) { + WOLFSSL_MSG("Memory error"); + return WOLFSSL_FAILURE; + } + #endif + + /* try to load each regular file in dir */ + ret = wc_ReadDirFirst(readCtx, dir, &name); + while (ret == 0 && name) { + WOLFSSL_MSG(name); + /* Try to process file with type DETECT_CERT_TYPE to parse the + correct certificate header and footer type */ + ret = ProcessFile(ctx, name, WOLFSSL_FILETYPE_PEM, DETECT_CERT_TYPE, + NULL, 0, str->cm->crl, 0); + /* Not failing on load errors */ + if (ret != WOLFSSL_SUCCESS) + WOLFSSL_MSG("Failed to load file in path, continuing"); + else + successes++; + + ret = wc_ReadDirNext(readCtx, dir, &name); + } + wc_ReadDirClose(readCtx); + + /* Success if at least one file in dir was loaded */ + if (successes > 0) + ret = WOLFSSL_SUCCESS; + else { + WOLFSSL_ERROR(ret); + ret = WOLFSSL_FAILURE; + } + + #ifdef WOLFSSL_SMALL_STACK + XFREE(readCtx, ctx->heap, DYNAMIC_TYPE_DIRCTX); + #endif + } + + ctx->cm = NULL; + wolfSSL_CTX_free(ctx); + + return ret; } #endif @@ -24496,26 +25544,156 @@ void wolfSSL_AES_cfb128_encrypt(const unsigned char *in, unsigned char* out, } #endif /* NO_AES */ -#ifndef NO_WOLFSSL_STUB +#ifndef NO_FILESYSTEM + #include /* var_arg */ + #ifdef __clang__ + #pragma clang diagnostic push + #pragma clang diagnostic ignored "-Wformat-nonliteral" + #endif +#endif + +#ifndef NO_FILESYSTEM +/* returns amount printed on success, negative in fail case */ int wolfSSL_BIO_printf(WOLFSSL_BIO* bio, const char* format, ...) { - (void)bio; - (void)format; - WOLFSSL_STUB("BIO_printf"); + int ret = -1; + va_list args; - return 0; + if (bio == NULL) + return WOLFSSL_FATAL_ERROR; + + va_start(args, format); + switch (bio->type) { + case WOLFSSL_BIO_FILE: + ret = vfprintf(bio->file, format, args); + break; + + case WOLFSSL_BIO_MEMORY: + #if defined(OPENSSL_EXTRA) && !defined(_WIN32) + case WOLFSSL_BIO_SSL: + { + char* pt = NULL; + ret = vasprintf(&pt, format, args); + if (ret > 0 && pt != NULL) { + wolfSSL_BIO_write(bio, pt, ret); + } + if (pt != NULL) { + free(pt); + } + } + break; + #endif + + default: + WOLFSSL_MSG("Unsupported WOLFSSL_BIO type for wolfSSL_BIO_printf"); + break; + } + va_end(args); + + return ret; } #endif -#ifndef NO_WOLFSSL_STUB +#if !defined(NO_FILESYSTEM) && defined(__clang__) +#pragma clang diagnostic pop +#endif + +#undef LINE_LEN +#define LINE_LEN 16 +int wolfSSL_BIO_dump(WOLFSSL_BIO *bio, const char *buf, int length) +{ + int ret = 0; + + if (bio == NULL) + return 0; + +#ifndef NO_FILESYSTEM + if (bio->type == WOLFSSL_BIO_FILE) { + int i; + char line[80]; + + if (!buf) { + return fputs("\tNULL", bio->file); + } + + sprintf(line, "\t"); + for (i = 0; i < LINE_LEN; i++) { + if (i < length) + sprintf(line + 1 + i * 3,"%02x ", buf[i]); + else + sprintf(line + 1 + i * 3, " "); + } + sprintf(line + 1 + LINE_LEN * 3, "| "); + for (i = 0; i < LINE_LEN; i++) { + if (i < length) { + sprintf(line + 3 + LINE_LEN * 3 + i, + "%c", 31 < buf[i] && buf[i] < 127 ? buf[i] : '.'); + } + } + ret += fputs(line, bio->file); + + if (length > LINE_LEN) + ret += wolfSSL_BIO_dump(bio, buf + LINE_LEN, length - LINE_LEN); + } +#else + (void)buf; + (void)length; +#endif + + return ret; +} + int wolfSSL_ASN1_UTCTIME_print(WOLFSSL_BIO* bio, const WOLFSSL_ASN1_UTCTIME* a) { - (void)bio; - (void)a; - WOLFSSL_STUB("ASN1_UTCTIME_print"); + WOLFSSL_ENTER("ASN1_UTCTIME_print"); + if (bio == NULL || a == NULL) { + return WOLFSSL_FAILURE; + } + if (a->data[0] != ASN_UTC_TIME) { + WOLFSSL_MSG("Error, not UTC_TIME"); + return WOLFSSL_FAILURE; + } + + return wolfSSL_ASN1_TIME_print(bio, a); +} + + +/* Checks the ASN1 syntax of "a" + * returns WOLFSSL_SUCCESS (1) if correct otherwise WOLFSSL_FAILURE (0) */ +int wolfSSL_ASN1_TIME_check(const WOLFSSL_ASN1_TIME* a) +{ + char buf[MAX_TIME_STRING_SZ]; + + WOLFSSL_ENTER("wolfSSL_ASN1_TIME_check"); + + /* if can parse the WOLFSSL_ASN1_TIME passed in then consider syntax good */ + if (wolfSSL_ASN1_TIME_to_string((WOLFSSL_ASN1_TIME*)a, buf, + MAX_TIME_STRING_SZ) == NULL) { + return WOLFSSL_FAILURE; + } + return WOLFSSL_SUCCESS; +} + +#ifndef NO_WOLFSSL_STUB +int wolfSSL_ASN1_TIME_diff(int *pday, int *psec, + const WOLFSSL_ASN1_TIME *from, const WOLFSSL_ASN1_TIME *to) +{ + WOLFSSL_STUB("wolfSSL_ASN1_TIME_diff"); + (void)pday; + (void)psec; + (void)from; + (void)to; return 0; } -#endif + +WOLFSSL_API WOLFSSL_ASN1_TIME *wolfSSL_ASN1_TIME_set(WOLFSSL_ASN1_TIME *s, time_t t) +{ + WOLFSSL_STUB("wolfSSL_ASN1_TIME_set"); + (void)s; + (void)t; + return s; +} +#endif /* !NO_WOLFSSL_STUB */ /* Return the month as a string. * @@ -24533,12 +25711,17 @@ static WC_INLINE const char* MonthStr(const char* n) int wolfSSL_ASN1_GENERALIZEDTIME_print(WOLFSSL_BIO* bio, const WOLFSSL_ASN1_GENERALIZEDTIME* asnTime) { - const char* p = (const char *)(asnTime->data + 2); + const char* p; WOLFSSL_ENTER("wolfSSL_ASN1_GENERALIZEDTIME_print"); if (bio == NULL || asnTime == NULL) return BAD_FUNC_ARG; + if (asnTime->data[0] != ASN_GENERALIZED_TIME) { + WOLFSSL_MSG("Error, not GENERALIZED_TIME"); + return WOLFSSL_FAILURE; + } + p = (const char *)(asnTime->data + 2); /* GetTimeString not always available. */ wolfSSL_BIO_write(bio, MonthStr(p + 4), 3); wolfSSL_BIO_write(bio, " ", 1); @@ -24584,7 +25767,6 @@ void* wolfSSL_sk_value(WOLF_STACK_OF(WOLFSSL_ASN1_OBJECT)* sk, int i) return (void*)sk->data.obj; } - /* Free the structure for ASN1_OBJECT stack */ void wolfSSL_sk_free(WOLFSSL_STACK* sk) { @@ -24615,6 +25797,9 @@ void wolfSSL_sk_free(WOLFSSL_STACK* sk) case STACK_TYPE_NULL: wolfSSL_sk_GENERIC_free(sk); break; + case STACK_TYPE_X509_NAME: + wolfSSL_sk_X509_NAME_free(sk); + break; #endif default: wolfSSL_sk_ASN1_OBJECT_free(sk); @@ -24732,10 +25917,22 @@ void wolfSSL_AUTHORITY_KEYID_free(WOLFSSL_AUTHORITY_KEYID *id) } XFREE(id, NULL, DYNAMIC_TYPE_OPENSSL); } + +int wolfSSL_sk_SSL_COMP_num(WOLF_STACK_OF(WOLFSSL_COMP)* sk) +{ + if (sk == NULL) + return 0; + return (int)sk->num; +} + #endif /* OPENSSL_EXTRA */ #if defined(OPENSSL_EXTRA) || defined(HAVE_EXT_CACHE) -/* stunnel 4.28 needs */ +/* stunnel 4.28 needs + * + * Callback that is called if a session tries to resume but could not find + * the session to resume it. + */ void wolfSSL_CTX_sess_set_get_cb(WOLFSSL_CTX* ctx, WOLFSSL_SESSION*(*f)(WOLFSSL*, unsigned char*, int, int*)) { @@ -26753,6 +27950,17 @@ WOLFSSL_BIGNUM *wolfSSL_BN_mod_inverse(WOLFSSL_BIGNUM *r, return r; } +#ifndef NO_WOLFSSL_STUB +WOLFSSL_ASN1_INTEGER *wolfSSL_BN_to_ASN1_INTEGER(const WOLFSSL_BIGNUM *bn, WOLFSSL_ASN1_INTEGER *ai) +{ + WOLFSSL_STUB("wolfSSL_BN_to_ASN1_INTEGER"); + (void)bn; + (void)ai; + return NULL; +} +#endif + + #ifndef NO_DH static void InitwolfSSL_DH(WOLFSSL_DH* dh) @@ -26894,6 +28102,63 @@ int wolfSSL_DH_size(WOLFSSL_DH* dh) return wolfSSL_BN_num_bytes(dh->p); } +/* This sets a big number with the 768-bit prime from RFC 2409. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_768_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A63A3620FFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_768_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 768 prime to big number"); + return NULL; + } + + return bn; +} + +/* This sets a big number with the 1024-bit prime from RFC 2409. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_1024_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE6" + "49286651ECE65381FFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_1024_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 1024 prime to big number"); + return NULL; + } + + return bn; +} /* This sets a big number with the 1536-bit prime from RFC 3526. * @@ -26929,6 +28194,300 @@ WOLFSSL_BIGNUM* wolfSSL_DH_1536_prime(WOLFSSL_BIGNUM* bn) return bn; } +/* This sets a big number with the 2048-bit prime from RFC 3526. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_2048_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE6" + "49286651ECE45B3DC2007CB8A163BF05" + "98DA48361C55D39A69163FA8FD24CF5F" + "83655D23DCA3AD961C62F356208552BB" + "9ED529077096966D670C354E4ABC9804" + "F1746C08CA18217C32905E462E36CE3B" + "E39E772C180E86039B2783A2EC07A28F" + "B5C55DF06F4C52C9DE2BCBF695581718" + "3995497CEA956AE515D2261898FA0510" + "15728E5A8AACAA68FFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_2048_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 2048 prime to big number"); + return NULL; + } + + return bn; +} + +/* This sets a big number with the 3072-bit prime from RFC 3526. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_3072_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE6" + "49286651ECE45B3DC2007CB8A163BF05" + "98DA48361C55D39A69163FA8FD24CF5F" + "83655D23DCA3AD961C62F356208552BB" + "9ED529077096966D670C354E4ABC9804" + "F1746C08CA18217C32905E462E36CE3B" + "E39E772C180E86039B2783A2EC07A28F" + "B5C55DF06F4C52C9DE2BCBF695581718" + "3995497CEA956AE515D2261898FA0510" + "15728E5A8AAAC42DAD33170D04507A33" + "A85521ABDF1CBA64ECFB850458DBEF0A" + "8AEA71575D060C7DB3970F85A6E1E4C7" + "ABF5AE8CDB0933D71E8C94E04A25619D" + "CEE3D2261AD2EE6BF12FFA06D98A0864" + "D87602733EC86A64521F2B18177B200C" + "BBE117577A615D6C770988C0BAD946E2" + "08E24FA074E5AB3143DB5BFCE0FD108E" + "4B82D120A93AD2CAFFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_3072_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 3072 prime to big number"); + return NULL; + } + + return bn; +} + +/* This sets a big number with the 4096-bit prime from RFC 3526. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_4096_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE6" + "49286651ECE45B3DC2007CB8A163BF05" + "98DA48361C55D39A69163FA8FD24CF5F" + "83655D23DCA3AD961C62F356208552BB" + "9ED529077096966D670C354E4ABC9804" + "F1746C08CA18217C32905E462E36CE3B" + "E39E772C180E86039B2783A2EC07A28F" + "B5C55DF06F4C52C9DE2BCBF695581718" + "3995497CEA956AE515D2261898FA0510" + "15728E5A8AAAC42DAD33170D04507A33" + "A85521ABDF1CBA64ECFB850458DBEF0A" + "8AEA71575D060C7DB3970F85A6E1E4C7" + "ABF5AE8CDB0933D71E8C94E04A25619D" + "CEE3D2261AD2EE6BF12FFA06D98A0864" + "D87602733EC86A64521F2B18177B200C" + "BBE117577A615D6C770988C0BAD946E2" + "08E24FA074E5AB3143DB5BFCE0FD108E" + "4B82D120A92108011A723C12A787E6D7" + "88719A10BDBA5B2699C327186AF4E23C" + "1A946834B6150BDA2583E9CA2AD44CE8" + "DBBBC2DB04DE8EF92E8EFC141FBECAA6" + "287C59474E6BC05D99B2964FA090C3A2" + "233BA186515BE7ED1F612970CEE2D7AF" + "B81BDD762170481CD0069127D5B05AA9" + "93B4EA988D8FDDC186FFB7DC90A6C08F" + "4DF435C934063199FFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_4096_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 4096 prime to big number"); + return NULL; + } + + return bn; +} + +/* This sets a big number with the 6144-bit prime from RFC 3526. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_6144_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE6" + "49286651ECE45B3DC2007CB8A163BF05" + "98DA48361C55D39A69163FA8FD24CF5F" + "83655D23DCA3AD961C62F356208552BB" + "9ED529077096966D670C354E4ABC9804" + "F1746C08CA18217C32905E462E36CE3B" + "E39E772C180E86039B2783A2EC07A28F" + "B5C55DF06F4C52C9DE2BCBF695581718" + "3995497CEA956AE515D2261898FA0510" + "15728E5A8AAAC42DAD33170D04507A33" + "A85521ABDF1CBA64ECFB850458DBEF0A" + "8AEA71575D060C7DB3970F85A6E1E4C7" + "ABF5AE8CDB0933D71E8C94E04A25619D" + "CEE3D2261AD2EE6BF12FFA06D98A0864" + "D87602733EC86A64521F2B18177B200C" + "BBE117577A615D6C770988C0BAD946E2" + "08E24FA074E5AB3143DB5BFCE0FD108E" + "4B82D120A92108011A723C12A787E6D7" + "88719A10BDBA5B2699C327186AF4E23C" + "1A946834B6150BDA2583E9CA2AD44CE8" + "DBBBC2DB04DE8EF92E8EFC141FBECAA6" + "287C59474E6BC05D99B2964FA090C3A2" + "233BA186515BE7ED1F612970CEE2D7AF" + "B81BDD762170481CD0069127D5B05AA9" + "93B4EA988D8FDDC186FFB7DC90A6C08F" + "4DF435C93402849236C3FAB4D27C7026" + "C1D4DCB2602646DEC9751E763DBA37BD" + "F8FF9406AD9E530EE5DB382F413001AE" + "B06A53ED9027D831179727B0865A8918" + "DA3EDBEBCF9B14ED44CE6CBACED4BB1B" + "DB7F1447E6CC254B332051512BD7AF42" + "6FB8F401378CD2BF5983CA01C64B92EC" + "F032EA15D1721D03F482D7CE6E74FEF6" + "D55E702F46980C82B5A84031900B1C9E" + "59E7C97FBEC7E8F323A97A7E36CC88BE" + "0F1D45B7FF585AC54BD407B22B4154AA" + "CC8F6D7EBF48E1D814CC5ED20F8037E0" + "A79715EEF29BE32806A1D58BB7C5DA76" + "F550AA3D8A1FBFF0EB19CCB1A313D55C" + "DA56C9EC2EF29632387FE8D76E3C0468" + "043E8F663F4860EE12BF2D5B0B7474D6" + "E694F91E6DCC4024FFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_6144_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 6144 prime to big number"); + return NULL; + } + + return bn; +} + + +/* This sets a big number with the 8192-bit prime from RFC 3526. + * + * bn if not NULL then the big number structure is used. If NULL then a new + * big number structure is created. + * + * Returns a WOLFSSL_BIGNUM structure on success and NULL with failure. + */ +WOLFSSL_BIGNUM* wolfSSL_DH_8192_prime(WOLFSSL_BIGNUM* bn) +{ + const char prm[] = { + "FFFFFFFFFFFFFFFFC90FDAA22168C234" + "C4C6628B80DC1CD129024E088A67CC74" + "020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F1437" + "4FE1356D6D51C245E485B576625E7EC6" + "F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE6" + "49286651ECE45B3DC2007CB8A163BF05" + "98DA48361C55D39A69163FA8FD24CF5F" + "83655D23DCA3AD961C62F356208552BB" + "9ED529077096966D670C354E4ABC9804" + "F1746C08CA18217C32905E462E36CE3B" + "E39E772C180E86039B2783A2EC07A28F" + "B5C55DF06F4C52C9DE2BCBF695581718" + "3995497CEA956AE515D2261898FA0510" + "15728E5A8AAAC42DAD33170D04507A33" + "A85521ABDF1CBA64ECFB850458DBEF0A" + "8AEA71575D060C7DB3970F85A6E1E4C7" + "ABF5AE8CDB0933D71E8C94E04A25619D" + "CEE3D2261AD2EE6BF12FFA06D98A0864" + "D87602733EC86A64521F2B18177B200C" + "BBE117577A615D6C770988C0BAD946E2" + "08E24FA074E5AB3143DB5BFCE0FD108E" + "4B82D120A92108011A723C12A787E6D7" + "88719A10BDBA5B2699C327186AF4E23C" + "1A946834B6150BDA2583E9CA2AD44CE8" + "DBBBC2DB04DE8EF92E8EFC141FBECAA6" + "287C59474E6BC05D99B2964FA090C3A2" + "233BA186515BE7ED1F612970CEE2D7AF" + "B81BDD762170481CD0069127D5B05AA9" + "93B4EA988D8FDDC186FFB7DC90A6C08F" + "4DF435C93402849236C3FAB4D27C7026" + "C1D4DCB2602646DEC9751E763DBA37BD" + "F8FF9406AD9E530EE5DB382F413001AE" + "B06A53ED9027D831179727B0865A8918" + "DA3EDBEBCF9B14ED44CE6CBACED4BB1B" + "DB7F1447E6CC254B332051512BD7AF42" + "6FB8F401378CD2BF5983CA01C64B92EC" + "F032EA15D1721D03F482D7CE6E74FEF6" + "D55E702F46980C82B5A84031900B1C9E" + "59E7C97FBEC7E8F323A97A7E36CC88BE" + "0F1D45B7FF585AC54BD407B22B4154AA" + "CC8F6D7EBF48E1D814CC5ED20F8037E0" + "A79715EEF29BE32806A1D58BB7C5DA76" + "F550AA3D8A1FBFF0EB19CCB1A313D55C" + "DA56C9EC2EF29632387FE8D76E3C0468" + "043E8F663F4860EE12BF2D5B0B7474D6" + "E694F91E6DBE115974A3926F12FEE5E4" + "38777CB6A932DF8CD8BEC4D073B931BA" + "3BC832B68D9DD300741FA7BF8AFC47ED" + "2576F6936BA424663AAB639C5AE4F568" + "3423B4742BF1C978238F16CBE39D652D" + "E3FDB8BEFC848AD922222E04A4037C07" + "13EB57A81A23F0C73473FC646CEA306B" + "4BCBC8862F8385DDFA9D4B7FA2C087E8" + "79683303ED5BDD3A062B3CF5B3A278A6" + "6D2A13F83F44F82DDF310EE074AB6A36" + "4597E899A0255DC164F31CC50846851D" + "F9AB48195DED7EA1B1D510BD7EE74D73" + "FAF36BC31ECFA268359046F4EB879F92" + "4009438B481C6CD7889A002ED5EE382B" + "C9190DA6FC026E479558E4475677E9AA" + "9E3050E2765694DFC81F56E880B96E71" + "60C980DD98EDD3DFFFFFFFFFFFFFFFFF" + }; + + WOLFSSL_ENTER("wolfSSL_DH_8192_prime"); + + if (wolfSSL_BN_hex2bn(&bn, prm) != SSL_SUCCESS) { + WOLFSSL_MSG("Error converting DH 8192 prime to big number"); + return NULL; + } + + return bn; +} /* return code compliant with OpenSSL : * 1 if success, 0 if error @@ -27088,6 +28647,59 @@ int wolfSSL_DH_compute_key(unsigned char* key, WOLFSSL_BIGNUM* otherPub, return ret; } + + +#if defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x10100000L +/* ownership of p,q,and g get taken over by "dh" on success and should be free'd + * with a call to wolfSSL_DH_free -- not individually. + * + * returns WOLFSSL_SUCCESS on success + */ +int wolfSSL_DH_set0_pqg(WOLFSSL_DH *dh, WOLFSSL_BIGNUM *p, + WOLFSSL_BIGNUM *q, WOLFSSL_BIGNUM *g) +{ + int ret; + WOLFSSL_ENTER("wolfSSL_DH_set0_pqg"); + + /* q can be NULL */ + if (dh == NULL || p == NULL || g == NULL) { + WOLFSSL_MSG("Bad function arguments"); + return WOLFSSL_FAILURE; + } + + /* free existing internal DH structure and recreate with new p / g */ + if (dh->inSet) { + ret = wc_FreeDhKey((DhKey*)dh->internal); + if (ret != 0) { + WOLFSSL_MSG("Unable to free internal DH key"); + return WOLFSSL_FAILURE; + } + } + + wolfSSL_BN_free(dh->p); + wolfSSL_BN_free(dh->q); + wolfSSL_BN_free(dh->g); + wolfSSL_BN_free(dh->pub_key); + wolfSSL_BN_free(dh->priv_key); + + dh->p = p; + dh->q = q; + dh->g = g; + + ret = SetDhInternal(dh); + if (ret != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Unable to set internal DH key"); + dh->p = NULL; + dh->q = NULL; + dh->g = NULL; + dh->inSet = 0; + return WOLFSSL_FAILURE; + } + + return WOLFSSL_SUCCESS; +} +#endif /* v1.1.0 or later */ + #endif /* NO_DH */ @@ -28622,6 +30234,27 @@ int wolfSSL_RSA_public_decrypt(int flen, const unsigned char* from, return tlen; } +void wolfSSL_RSA_get0_key(const WOLFSSL_RSA *r, const WOLFSSL_BIGNUM **n, + const WOLFSSL_BIGNUM **e, const WOLFSSL_BIGNUM **d) +{ + WOLFSSL_ENTER("wolfSSL_RSA_get0_key"); + + if (r != NULL) { + if (n != NULL) + *n = r->n; + if (e != NULL) + *e = r->e; + if (d != NULL) + *d = r->d; + } else { + if (n != NULL) + *n = NULL; + if (e != NULL) + *e = NULL; + if (d != NULL) + *d = NULL; + } +} /* generate p-1 and q-1, WOLFSSL_SUCCESS on ok */ int wolfSSL_RSA_GenAdd(WOLFSSL_RSA* rsa) @@ -30256,6 +31889,45 @@ WOLFSSL_EC_KEY *wolfSSL_EC_KEY_new_by_curve_name(int nid) return key; } +typedef struct { + const char *name; + int nid; +} WOLF_EC_NIST_NAME; +static const WOLF_EC_NIST_NAME kNistCurves[] = { + {"P-192", NID_X9_62_prime192v1}, + {"P-256", NID_X9_62_prime256v1}, + {"P-112", NID_secp112r1}, + {"P-112-2", NID_secp112r2}, + {"P-128", NID_secp128r1}, + {"P-128-2", NID_secp128r2}, + {"P-160", NID_secp160r1}, + {"P-160-2", NID_secp160r2}, + {"P-224", NID_secp224r1}, + {"P-384", NID_secp384r1}, + {"P-521", NID_secp521r1}, + {"K-160", NID_secp160k1}, + {"K-192", NID_secp192k1}, + {"K-224", NID_secp224k1}, + {"K-256", NID_secp256k1}, + {"B-160", NID_brainpoolP160r1}, + {"B-192", NID_brainpoolP192r1}, + {"B-224", NID_brainpoolP224r1}, + {"B-256", NID_brainpoolP256r1}, + {"B-320", NID_brainpoolP320r1}, + {"B-384", NID_brainpoolP384r1}, + {"B-512", NID_brainpoolP512r1}, +}; +const char* wolfSSL_EC_curve_nid2nist(int nid) +{ + int i; + for (i = 0; i < (int)(sizeof(kNistCurves)/sizeof(WOLF_EC_NIST_NAME)); i++) { + if (kNistCurves[i].nid == nid) { + return kNistCurves[i].name; + } + } + return NULL; +} + #endif /* HAVE_ECC */ #endif /* OPENSSL_EXTRA */ @@ -32029,6 +33701,34 @@ WOLFSSL_RSA* wolfSSL_PEM_read_bio_RSAPrivateKey(WOLFSSL_BIO* bio, #endif /* !NO_RSA */ +#ifdef HAVE_ECC +/* returns a new WOLFSSL_EC_GROUP structure on success and NULL on fail */ +WOLFSSL_EC_GROUP* wolfSSL_PEM_read_bio_ECPKParameters(WOLFSSL_BIO* bio, + WOLFSSL_EC_GROUP** group, pem_password_cb* cb, void* pass) +{ + WOLFSSL_EVP_PKEY* pkey = NULL; + WOLFSSL_EC_GROUP* ret = NULL; + + /* check on if bio is null is done in wolfSSL_PEM_read_bio_PrivateKey */ + pkey = wolfSSL_PEM_read_bio_PrivateKey(bio, NULL, cb, pass); + if (pkey != NULL) { + if (pkey->type != EVP_PKEY_EC) { + WOLFSSL_MSG("Unexpected key type"); + } + else { + ret = (WOLFSSL_EC_GROUP*)wolfSSL_EC_KEY_get0_group(pkey->ecc); + + /* set ecc group to null so it is not free'd when pkey is free'd */ + pkey->ecc->group = NULL; + } + } + + (void)group; + wolfSSL_EVP_PKEY_free(pkey); + return ret; +} +#endif /* HAVE_ECC */ + /* return of pkey->type which will be EVP_PKEY_RSA for example. * * type type of EVP_PKEY @@ -32612,10 +34312,45 @@ int wolfSSL_EC_KEY_LoadDer_ex(WOLFSSL_EC_KEY* key, const unsigned char* derBuf, } #endif /* HAVE_ECC */ - #endif /* OPENSSL_EXTRA */ +#if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL) + +/* increments ref count of WOLFSSL_X509. Return 1 on success, 0 on error */ +int wolfSSL_X509_up_ref(WOLFSSL_X509* x509) +{ + if (x509) { + if (wc_LockMutex(&x509->refMutex) != 0) { + WOLFSSL_MSG("Failed to lock x509 mutex"); + } + x509->refCount++; + wc_UnLockMutex(&x509->refMutex); + + return 1; + } + + return 0; +} + +/* increments ref count of WOLFSSL_EVP_PKEY. Return 1 on success, 0 on error */ +int wolfSSL_EVP_PKEY_up_ref(WOLFSSL_EVP_PKEY* pkey) +{ + if (pkey) { + if (wc_LockMutex(&pkey->refMutex) != 0) { + WOLFSSL_MSG("Failed to lock pkey mutex"); + } + pkey->references++; + wc_UnLockMutex(&pkey->refMutex); + + return 1; + } + + return 0; +} +#endif /* OPENSSL_EXTRA || OPENSSL_ALL */ + + #ifdef WOLFSSL_ALT_CERT_CHAINS int wolfSSL_is_peer_alt_cert_chain(const WOLFSSL* ssl) { @@ -33176,6 +34911,47 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) return name; } + /* Creates a duplicate of a WOLFSSL_X509_NAME structure. + Returns a new WOLFSSL_X509_NAME structure or NULL on failure */ + WOLFSSL_X509_NAME* wolfSSL_X509_NAME_dup(WOLFSSL_X509_NAME* name) + { + WOLFSSL_X509_NAME* dup; + + WOLFSSL_ENTER("wolfSSL_X509_NAME_dup"); + + if (name == NULL) { + WOLFSSL_MSG("NULL parameter"); + return NULL; + } + + dup = (WOLFSSL_X509_NAME*)XMALLOC(sizeof(WOLFSSL_X509_NAME), NULL, + DYNAMIC_TYPE_X509); + if (dup == NULL) { + WOLFSSL_MSG("Malloc error"); + return NULL; + } + XMEMCPY(dup, name, sizeof(WOLFSSL_X509_NAME)); + InitX509Name(dup, 1); + + XMEMCPY(dup->name, name->name, name->sz); + dup->sz = name->sz; + dup->dynamicName = name->dynamicName; + #if defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL) + dup->fullName.fullName = (char*)XMALLOC(name->fullName.fullNameLen, + NULL, DYNAMIC_TYPE_X509); + if (dup->fullName.fullName != NULL) + XMEMCPY(dup->fullName.fullName, name->fullName.fullName, + name->fullName.fullNameLen); + dup->x509 = name->x509; + #endif + #if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) + dup->rawLen = min(name->rawLen, sizeof(dup->raw)); + XMEMCPY(dup->raw, name->raw, dup->rawLen); + #endif + + return dup; + } + #if defined(WOLFSSL_CERT_GEN) /* helper function for CopyX509NameToCertName() @@ -33340,6 +35116,432 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) return WOLFSSL_SUCCESS; } +#ifdef WOLFSSL_CERT_REQ + static int ReqCertFromX509(Cert* cert, WOLFSSL_X509* req) + { + int ret; + + if (wc_InitCert(cert) != 0) + return WOLFSSL_FAILURE; + + ret = CopyX509NameToCertName(&req->subject, &cert->subject); + if (ret == WOLFSSL_SUCCESS) { + cert->version = req->version; + cert->isCA = req->isCa; +#ifdef WOLFSSL_CERT_EXT + if (req->subjKeyIdSz != 0) { + XMEMCPY(cert->skid, req->subjKeyId, req->subjKeyIdSz); + cert->skidSz = req->subjKeyIdSz; + } + if (req->keyUsageSet) + cert->keyUsage = req->keyUsage; + /* Extended Key Usage not supported. */ +#endif + } + + return ret; + } +#endif + + /* convert a WOLFSSL_X509 to a Cert structure for writing out */ + static int CertFromX509(Cert* cert, WOLFSSL_X509* x509) + { + int ret; + #ifdef WOLFSSL_CERT_EXT + int i; + #endif + + WOLFSSL_ENTER("wolfSSL_X509_to_Cert()"); + + if (x509 == NULL || cert == NULL) { + return BAD_FUNC_ARG; + } + + wc_InitCert(cert); + + cert->version = (int)wolfSSL_X509_get_version(x509); + + #ifdef WOLFSSL_ALT_NAMES + if (x509->notBefore.length < CTC_DATE_SIZE) { + XMEMCPY(cert->beforeDate, x509->notBefore.data, + x509->notBefore.length); + cert->beforeDateSz = x509->notBefore.length; + } + else { + WOLFSSL_MSG("Not before date too large"); + return WOLFSSL_FAILURE; + } + + if (x509->notAfter.length < CTC_DATE_SIZE) { + XMEMCPY(cert->afterDate, x509->notAfter.data, + x509->notAfter.length); + cert->afterDateSz = x509->notAfter.length; + } + else { + WOLFSSL_MSG("Not after date too large"); + return WOLFSSL_FAILURE; + } + + /* copy over alt names */ + { + int idx = 0; + DNS_entry* dns = x509->altNames; + + while (dns != NULL) { + int sz = (int)XSTRLEN(dns->name); + + if (sz < 0 || sz + idx > CTC_MAX_ALT_SIZE) { + WOLFSSL_MSG("Issue with copying over alt names"); + return WOLFSSL_FAILURE; + } + XMEMCPY(cert->altNames, dns->name, sz); + idx += sz; + dns = dns->next; + } + cert->altNamesSz = idx; + } + #endif + + cert->sigType = wolfSSL_X509_get_signature_type(x509); + cert->keyType = x509->pubKeyOID; + cert->isCA = wolfSSL_X509_get_isCA(x509); + + #ifdef WOLFSSL_CERT_EXT + if (x509->subjKeyIdSz < CTC_MAX_SKID_SIZE) { + XMEMCPY(cert->skid, x509->subjKeyId, x509->subjKeyIdSz); + cert->skidSz = (int)x509->subjKeyIdSz; + } + else { + WOLFSSL_MSG("Subject Key ID too large"); + return WOLFSSL_FAILURE; + } + + if (x509->authKeyIdSz < CTC_MAX_AKID_SIZE) { + XMEMCPY(cert->akid, x509->authKeyId, x509->authKeyIdSz); + cert->akidSz = (int)x509->authKeyIdSz; + } + else { + WOLFSSL_MSG("Auth Key ID too large"); + return WOLFSSL_FAILURE; + } + + for (i = 0; i < x509->certPoliciesNb; i++) { + /* copy the smaller of MAX macros, by default they are currently equal*/ + if ((int)CTC_MAX_CERTPOL_SZ <= (int)MAX_CERTPOL_SZ) { + XMEMCPY(cert->certPolicies[i], x509->certPolicies[i], + CTC_MAX_CERTPOL_SZ); + } + else { + XMEMCPY(cert->certPolicies[i], x509->certPolicies[i], + MAX_CERTPOL_SZ); + } + } + cert->certPoliciesNb = (word16)x509->certPoliciesNb; + + cert->keyUsage = x509->keyUsage; + #endif /* WOLFSSL_CERT_EXT */ + + #ifdef WOLFSSL_CERT_REQ + /* copy over challenge password for REQ certs */ + XMEMCPY(cert->challengePw, x509->challengePw, CTC_NAME_SIZE); + #endif + + if (x509->serialSz <= CTC_SERIAL_SIZE) { + XMEMCPY(cert->serial, x509->serial, x509->serialSz); + } + else { + WOLFSSL_MSG("Serial size error"); + return WOLFSSL_FAILURE; + } + + /* copy over Name structures */ + if ((ret = CopyX509NameToCertName(&(x509->issuer), &(cert->issuer))) + != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Error copying over issuer names"); + WOLFSSL_LEAVE("wolfSSL_X509_to_Cert()", ret); + return WOLFSSL_FAILURE; + } + if ((ret = CopyX509NameToCertName(&(x509->subject), &(cert->subject))) + != WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Error copying over subject names"); + WOLFSSL_LEAVE("wolfSSL_X509_to_Cert()", ret); + return WOLFSSL_FAILURE; + } + + cert->heap = x509->heap; + + return WOLFSSL_SUCCESS; + } + + + /* returns the sig type to use on success i.e CTC_SHAwRSA and WOLFSSL_FALURE + * on fail case */ + static int wolfSSL_sigTypeFromPKEY(WOLFSSL_EVP_MD* md, + WOLFSSL_EVP_PKEY* pkey) + { + int hashType; + int sigType = WOLFSSL_FAILURE; + + /* Convert key type and hash algorithm to a signature algorithm */ + if (wolfSSL_EVP_get_hashinfo(md, &hashType, NULL) == WOLFSSL_FAILURE) + return WOLFSSL_FAILURE; + + + if (pkey->type == EVP_PKEY_RSA) { + switch (hashType) { + case WC_HASH_TYPE_SHA: + sigType = CTC_SHAwRSA; + break; + case WC_HASH_TYPE_SHA224: + sigType = CTC_SHA224wRSA; + break; + case WC_HASH_TYPE_SHA256: + sigType = CTC_SHA256wRSA; + break; + case WC_HASH_TYPE_SHA384: + sigType = CTC_SHA384wRSA; + break; + case WC_HASH_TYPE_SHA512: + sigType = CTC_SHA512wRSA; + break; + default: + return WOLFSSL_FAILURE; + } + } + else if (pkey->type == EVP_PKEY_EC) { + switch (hashType) { + case WC_HASH_TYPE_SHA: + sigType = CTC_SHAwECDSA; + break; + case WC_HASH_TYPE_SHA224: + sigType = CTC_SHA224wECDSA; + break; + case WC_HASH_TYPE_SHA256: + sigType = CTC_SHA256wECDSA; + break; + case WC_HASH_TYPE_SHA384: + sigType = CTC_SHA384wECDSA; + break; + case WC_HASH_TYPE_SHA512: + sigType = CTC_SHA512wECDSA; + break; + default: + return WOLFSSL_FAILURE; + } + } + else + return WOLFSSL_FAILURE; + return sigType; + } + + + /* generates DER buffer from WOLFSSL_X509 + * If req == 1 then creates a request DER buffer + * + * updates derSz with certificate body size on success + * return WOLFSSL_SUCCESS on success + */ + static int wolfSSL_X509_make_der(WOLFSSL_X509* x509, int req, + unsigned char* der, int* derSz) + { + int ret; + Cert cert; + void* key = NULL; + int type = -1; + #ifndef NO_RSA + RsaKey rsa; + #endif + #ifdef HAVE_ECC + ecc_key ecc; + #endif + WC_RNG rng; + word32 idx = 0; + + if (x509 == NULL || der == NULL || derSz == NULL) + return BAD_FUNC_ARG; + + #ifndef WOLFSSL_CERT_REQ + if (req) { + WOLFSSL_MSG("WOLFSSL_CERT_REQ needed for certificate request"); + return WOLFSSL_FAILURE; + } + #endif + + #ifdef WOLFSSL_CERT_REQ + if (req) { + if (ReqCertFromX509(&cert, x509) != WOLFSSL_SUCCESS) + return WOLFSSL_FAILURE; + } + else + #endif + { + /* Create a Cert that has the certificate fields. */ + if (CertFromX509(&cert, x509) != WOLFSSL_SUCCESS) + return WOLFSSL_FAILURE; + } + + /* Create a public key object from requests public key. */ + #ifndef NO_RSA + if (x509->pubKeyOID == RSAk) { + type = RSA_TYPE; + ret = wc_InitRsaKey(&rsa, x509->heap); + if (ret != 0) + return ret; + ret = wc_RsaPublicKeyDecode(x509->pubKey.buffer, &idx, &rsa, + x509->pubKey.length); + if (ret != 0) { + wc_FreeRsaKey(&rsa); + return ret; + } + key = (void*)&rsa; + } + #endif + #ifdef HAVE_ECC + if (x509->pubKeyOID == ECDSAk) { + type = ECC_TYPE; + ret = wc_ecc_init(&ecc); + if (ret != 0) + return ret; + ret = wc_EccPublicKeyDecode(x509->pubKey.buffer, &idx, &ecc, + x509->pubKey.length); + if (ret != 0) { + wc_ecc_free(&ecc); + return ret; + } + key = (void*)&ecc; + } + #endif + if (key == NULL) + return WOLFSSL_FAILURE; + + /* Make the body of the certificate request. */ + #ifdef WOLFSSL_CERT_REQ + if (req) { + ret = wc_MakeCertReq_ex(&cert, der, *derSz, type, key); + } + else + #endif + { + ret = wc_InitRng(&rng); + if (ret != 0) + return WOLFSSL_FAILURE; + + ret = wc_MakeCert_ex(&cert, der, *derSz, type, key, &rng); + wc_FreeRng(&rng); + } + if (ret < 0) { + return ret; + } + + /* Dispose of the public key object. */ + #ifndef NO_RSA + if (x509->pubKeyOID == RSAk) + wc_FreeRsaKey(&rsa); + #endif + #ifdef HAVE_ECC + if (x509->pubKeyOID == ECDSAk) + wc_ecc_free(&ecc); + #endif + *derSz = ret; + + return WOLFSSL_SUCCESS; + } + + + /* signs a der buffer for the WOLFSSL_X509 structure using the PKEY and MD + * hash passed in + * + * WARNING: this free's and replaces the existing DER buffer in the + * WOLFSSL_X509 with the newly signed buffer. + * returns size of signed buffer on success and negative values on fail + */ + static int wolfSSL_X509_resign_cert(WOLFSSL_X509* x509, int req, + unsigned char* der, int derSz, int certBodySz, WOLFSSL_EVP_MD* md, + WOLFSSL_EVP_PKEY* pkey) + { + int ret; + void* key = NULL; + int type = -1; + int sigType; + WC_RNG rng; + + sigType = wolfSSL_sigTypeFromPKEY(md, pkey); + if (sigType == WOLFSSL_FAILURE) + return WOLFSSL_FATAL_ERROR; + + + /* Get the private key object and type from pkey. */ + #ifndef NO_RSA + if (pkey->type == EVP_PKEY_RSA) { + type = RSA_TYPE; + key = pkey->rsa->internal; + } + #endif + #ifdef HAVE_ECC + if (pkey->type == EVP_PKEY_EC) { + type = ECC_TYPE; + key = pkey->ecc->internal; + } + #endif + + /* Sign the certificate request body. */ + ret = wc_InitRng(&rng); + if (ret != 0) + return ret; + ret = wc_SignCert_ex(certBodySz, sigType, der, derSz, type, key, &rng); + wc_FreeRng(&rng); + if (ret < 0) + return ret; + + /* Put in the new certificate encoding into the x509 object. */ + FreeDer(&x509->derCert); + type = CERT_TYPE; + #ifdef WOLFSSL_REQ_CERT + if (req) { + type = CERTREQ_TYPE; + } + #endif + + if (AllocDer(&x509->derCert, ret, type, NULL) != 0) + return WOLFSSL_FATAL_ERROR; + XMEMCPY(x509->derCert->buffer, der, ret); + x509->derCert->length = ret; + + (void)req; + return ret; + } + + + /* returns the size of signature on success */ + int wolfSSL_X509_sign(WOLFSSL_X509* x509, WOLFSSL_EVP_PKEY* pkey, + const WOLFSSL_EVP_MD* md) + { + int ret; + byte der[4096]; /* @TODO dynamic set based on expected cert size */ + int derSz = sizeof(der); + + WOLFSSL_ENTER("wolfSSL_X509_sign"); + + if (x509 == NULL || pkey == NULL || md == NULL) + return WOLFSSL_FAILURE; + + x509->sigOID = wolfSSL_sigTypeFromPKEY((WOLFSSL_EVP_MD*)md, pkey); + if ((ret = wolfSSL_X509_make_der(x509, 0, der, &derSz)) != + WOLFSSL_SUCCESS) { + WOLFSSL_MSG("Unable to make DER for X509"); + WOLFSSL_LEAVE("wolfSSL_X509_sign", ret); + return WOLFSSL_FAILURE; + } + + ret = wolfSSL_X509_resign_cert(x509, 0, der, sizeof(der), derSz, + (WOLFSSL_EVP_MD*)md, pkey); + if (ret <= 0) { + WOLFSSL_LEAVE("wolfSSL_X509_sign", ret); + return WOLFSSL_FAILURE; + } + return ret; + } + /* Converts the x509 name structure into DER format. * @@ -33354,6 +35556,7 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) CertName cName; unsigned char buf[256]; /* ASN_MAX_NAME */ int sz; + WOLFSSL_ENTER("wolfSSL_i2d_X509_NAME"); if (out == NULL || name == NULL) { return BAD_FUNC_ARG; @@ -33985,8 +36188,147 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) return wolfSSL_PEM_read_bio_X509(bp, x, cb, u); } + +#ifdef OPENSSL_ALL + /* create and return a new WOLFSSL_X509_PKEY structure or NULL on failure */ + static WOLFSSL_X509_PKEY* wolfSSL_X509_PKEY_new(void* heap) + { + WOLFSSL_X509_PKEY* ret; + + ret = (WOLFSSL_X509_PKEY*)XMALLOC(sizeof(WOLFSSL_X509_PKEY), heap, + DYNAMIC_TYPE_KEY); + if (ret != NULL) { + XMEMSET(ret, 0, sizeof(WOLFSSL_X509_PKEY)); + ret->heap = heap; + } + return ret; + } + + + /* sets the values of X509_PKEY based on certificate passed in + * return WOLFSSL_SUCCESS on success */ + static int wolfSSL_X509_PKEY_set(WOLFSSL_X509_PKEY* xPkey, + WOLFSSL_X509* x509) + { + if (xPkey == NULL || x509 == NULL) { + return BAD_FUNC_ARG; + } + wolfSSL_EVP_PKEY_free(xPkey->dec_pkey); + xPkey->dec_pkey = wolfSSL_X509_get_pubkey(x509); + if (xPkey->dec_pkey == NULL) { + return WOLFSSL_FAILURE; + } + return WOLFSSL_SUCCESS; + } + + + /* free up all memory used by "xPkey" passed in */ + static void wolfSSL_X509_PKEY_free(WOLFSSL_X509_PKEY* xPkey) + { + if (xPkey != NULL) { + wolfSSL_EVP_PKEY_free(xPkey->dec_pkey); + } + XFREE(xPkey, xPkey->heap, DYNAMIC_TYPE_KEY); + } + + + /* Takes control of x509 on success + * helper function to break out code needed to set WOLFSSL_X509_INFO up + * free's "info" passed in if is not defaults + * + * returns WOLFSSL_SUCCESS on success + */ + static int wolfSSL_X509_INFO_set(WOLFSSL_X509_INFO* info, + WOLFSSL_X509* x509) + { + if (info == NULL || x509 == NULL) { + return BAD_FUNC_ARG; + } + + /* check is fresh "info" passed in, if not free it */ + if (info->x509 != NULL || info->x_pkey != NULL) { + WOLFSSL_X509_INFO* tmp; + + tmp = wolfSSL_X509_INFO_new(); + if (tmp == NULL) { + WOLFSSL_MSG("Unable to create new structure"); + return MEMORY_E; + } + wolfSSL_X509_INFO_free(info); + info = tmp; + } + + info->x509 = x509; + + //@TODO info->num + //@TODO info->enc_cipher + //@TODO info->enc_len + //@TODO info->enc_data + //@TODO info->crl + + info->x_pkey = wolfSSL_X509_PKEY_new(x509->heap); + return wolfSSL_X509_PKEY_set(info->x_pkey, x509); + } + + + /* + * bio WOLFSSL_BIO to read certificates from + * sk possible stack to push more X509_INFO structs to. Can be NULL + * cb callback password for encrypted PEM certificates + * u user input such as password + * + * returns stack on success and NULL or default stack passed in on fail + */ + WOLF_STACK_OF(WOLFSSL_X509_INFO)* wolfSSL_PEM_X509_INFO_read_bio( + WOLFSSL_BIO* bio, WOLF_STACK_OF(WOLFSSL_X509_INFO)* sk, + pem_password_cb* cb, void* u) + { + WOLF_STACK_OF(WOLFSSL_X509_INFO)* localSk; + WOLFSSL_X509* x509 = NULL; + int ret = WOLFSSL_SUCCESS; + + WOLFSSL_ENTER("wolfSSL_PEM_X509_INFO_read_bio"); + + /* attempt to used passed in stack or create a new one */ + if (sk != NULL) { + localSk = sk; + } + else { + localSk = wolfSSL_sk_X509_INFO_new_null(); + } + if (localSk == NULL) { + WOLFSSL_LEAVE("wolfSSL_PEM_X509_INFO_read_bio", MEMORY_E); + return NULL; + } + + /* parse through BIO and push new info's found onto stack */ + do { + x509 = wolfSSL_PEM_read_bio_X509(bio, NULL, cb, u); + if (x509 != NULL) { + WOLFSSL_X509_INFO* current; + + current = wolfSSL_X509_INFO_new(); + if (current == NULL) { + WOLFSSL_LEAVE("wolfSSL_PEM_X509_INFO_read_bio", MEMORY_E); + return NULL; + } + ret = wolfSSL_X509_INFO_set(current, x509); + if (ret != WOLFSSL_SUCCESS) { + wolfSSL_X509_free(x509); + } + else { + wolfSSL_sk_X509_INFO_push(localSk, current); + } + } + } while (x509 != NULL && ret == WOLFSSL_SUCCESS); + WOLFSSL_LEAVE("wolfSSL_PEM_X509_INFO_read_bio", ret); + return localSk; + } +#endif /* OPENSSL_ALL */ + void wolfSSL_X509_NAME_ENTRY_free(WOLFSSL_X509_NAME_ENTRY* ne) { + WOLFSSL_ENTER("wolfSSL_X509_NAME_ENTRY_free"); if (ne != NULL) { if (ne->value != NULL && ne->value != &(ne->data)) { wolfSSL_ASN1_STRING_free(ne->value); @@ -34367,188 +36709,213 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) int id; word32 type; const char* sName; + const char* lName; } WOLFSSL_ObjectInfo; static WOLFSSL_ObjectInfo wolfssl_object_info[] = { /* oidHashType */ #ifdef WOLFSSL_MD2 - { NID_md2, MD2h, oidHashType, "md2" }, + { NID_md2, MD2h, oidHashType, "md2", "md2"}, #endif #ifdef WOLFSSL_MD5 - { NID_md5, MD5h, oidHashType, "md5" }, + { NID_md5, MD5h, oidHashType, "md5", "md5"}, #endif #ifndef NO_SHA - { NID_sha1, SHAh, oidHashType, "sha" }, + { NID_sha1, SHAh, oidHashType, "sha", "sha1"}, #endif #ifdef WOLFSSL_SHA224 - { NID_sha224, SHA224h, oidHashType, "sha224" }, + { NID_sha224, SHA224h, oidHashType, "sha224", "sha224"}, #endif #ifndef NO_SHA256 - { NID_sha256, SHA256h, oidHashType, "sha256" }, + { NID_sha256, SHA256h, oidHashType, "sha256", "sha256"}, #endif #ifdef WOLFSSL_SHA384 - { NID_sha384, SHA384h, oidHashType, "sha384" }, + { NID_sha384, SHA384h, oidHashType, "sha384", "sha384"}, #endif #ifdef WOLFSSL_SHA512 - { NID_sha512, SHA512h, oidHashType, "sha512" }, + { NID_sha512, SHA512h, oidHashType, "sha512", "sha512"}, #endif /* oidSigType */ #ifndef NO_DSA #ifndef NO_SHA - { CTC_SHAwDSA, CTC_SHAwDSA, oidSigType, "shaWithDSA" }, + { CTC_SHAwDSA, CTC_SHAwDSA, oidSigType, "shaWithDSA", "dsaWithSHA1"}, #endif #endif /* NO_DSA */ #ifndef NO_RSA #ifdef WOLFSSL_MD2 - { CTC_MD2wRSA, CTC_MD2wRSA, oidSigType, "md2WithRSA" }, + { CTC_MD2wRSA, CTC_MD2wRSA, oidSigType, "md2WithRSA", + "md2WithRSAEncryption"}, #endif #ifndef NO_MD5 - { CTC_MD5wRSA, CTC_MD5wRSA, oidSigType, "md5WithRSA" }, + { CTC_MD5wRSA, CTC_MD5wRSA, oidSigType, "md5WithRSA", + "md5WithRSAEncryption"}, #endif #ifndef NO_SHA - { CTC_SHAwRSA, CTC_SHAwRSA, oidSigType, "shaWithRSA" }, + { CTC_SHAwRSA, CTC_SHAwRSA, oidSigType, "shaWithRSA", + "sha1WithRSAEncryption"}, #endif #ifdef WOLFSSL_SHA224 - { CTC_SHA224wRSA, CTC_SHA224wRSA, oidSigType, "sha224WithRSA" }, + { CTC_SHA224wRSA, CTC_SHA224wRSA, oidSigType, "sha224WithRSA", + "sha224WithRSAEncryption"}, #endif #ifndef NO_SHA256 - { CTC_SHA256wRSA, CTC_SHA256wRSA, oidSigType, "sha256WithRSA" }, + { CTC_SHA256wRSA, CTC_SHA256wRSA, oidSigType, "sha256WithRSA", + "sha256WithRSAEncryption"}, #endif #ifdef WOLFSSL_SHA384 - { CTC_SHA384wRSA, CTC_SHA384wRSA, oidSigType, "sha384WithRSA" }, + { CTC_SHA384wRSA, CTC_SHA384wRSA, oidSigType, "sha384WithRSA", + "sha384WithRSAEncryption"}, #endif #ifdef WOLFSSL_SHA512 - { CTC_SHA512wRSA, CTC_SHA512wRSA, oidSigType, "sha512WithRSA" }, + { CTC_SHA512wRSA, CTC_SHA512wRSA, oidSigType, "sha512WithRSA", + "sha512WithRSAEncryption"}, #endif #endif /* NO_RSA */ #ifdef HAVE_ECC #ifndef NO_SHA - { CTC_SHAwECDSA, CTC_SHAwECDSA, oidSigType, "shaWithECDSA" }, + { CTC_SHAwECDSA, CTC_SHAwECDSA, oidSigType, "shaWithECDSA", ""}, #endif #ifdef WOLFSSL_SHA224 - { CTC_SHA224wECDSA, CTC_SHA224wECDSA, oidSigType, "sha224WithECDSA" }, + { CTC_SHA224wECDSA, CTC_SHA224wECDSA, oidSigType, "sha224WithECDSA",""}, #endif #ifndef NO_SHA256 - { CTC_SHA256wECDSA, CTC_SHA256wECDSA, oidSigType, "sha256WithECDSA" }, + { CTC_SHA256wECDSA, CTC_SHA256wECDSA, oidSigType, "sha256WithECDSA",""}, #endif #ifdef WOLFSSL_SHA384 - { CTC_SHA384wECDSA, CTC_SHA384wECDSA, oidSigType, "sha384WithECDSA" }, + { CTC_SHA384wECDSA, CTC_SHA384wECDSA, oidSigType, "sha384WithECDSA",""}, #endif #ifdef WOLFSSL_SHA512 - { CTC_SHA512wECDSA, CTC_SHA512wECDSA, oidSigType, "sha512WithECDSA" }, + { CTC_SHA512wECDSA, CTC_SHA512wECDSA, oidSigType, "sha512WithECDSA",""}, #endif #endif /* HAVE_ECC */ /* oidKeyType */ #ifndef NO_DSA - { DSAk, DSAk, oidKeyType, "DSA key" }, + { DSAk, DSAk, oidKeyType, "DSA key", "dsaEncryption"}, #endif /* NO_DSA */ #ifndef NO_RSA - { RSAk, RSAk, oidKeyType, "RSA key" }, + { RSAk, RSAk, oidKeyType, "RSA key", "rsaEncryption"}, #endif /* NO_RSA */ #ifdef HAVE_NTRU - { NTRUk, NTRUk, oidKeyType, "NTRU key" }, + { NTRUk, NTRUk, oidKeyType, "NTRU key", "ntruEncryption"}, #endif /* HAVE_NTRU */ #ifdef HAVE_ECC - { ECDSAk, ECDSAk, oidKeyType, "ECDSA key" }, + { ECDSAk, ECDSAk, oidKeyType, "ECDSA key", "ecdsaEncryption"}, #endif /* HAVE_ECC */ /* oidBlkType */ #ifdef WOLFSSL_AES_128 - { AES128CBCb, AES128CBCb, oidBlkType, "AES-128-CBC" }, + { AES128CBCb, AES128CBCb, oidBlkType, "AES-128-CBC", "aes-128-cbc"}, #endif #ifdef WOLFSSL_AES_192 - { AES192CBCb, AES192CBCb, oidBlkType, "AES-192-CBC" }, + { AES192CBCb, AES192CBCb, oidBlkType, "AES-192-CBC", "aes-192-cbc"}, #endif #ifdef WOLFSSL_AES_256 - { AES256CBCb, AES256CBCb, oidBlkType, "AES-256-CBC" }, + { AES256CBCb, AES256CBCb, oidBlkType, "AES-256-CBC", "aes-256-cbc"}, #endif #ifndef NO_DES3 - { NID_des, DESb, oidBlkType, "DES-CBC" }, - { NID_des3, DES3b, oidBlkType, "DES3-CBC" }, + { NID_des, DESb, oidBlkType, "DES-CBC", "des-cbc"}, + { NID_des3, DES3b, oidBlkType, "DES3-CBC", "des3-cbc"}, #endif /* !NO_DES3 */ /* oidOcspType */ #ifdef HAVE_OCSP - { NID_id_pkix_OCSP_basic, OCSP_BASIC_OID, oidOcspType, "OCSP_basic" }, - { OCSP_NONCE_OID, OCSP_NONCE_OID, oidOcspType, "OCSP_nonce" }, + { NID_id_pkix_OCSP_basic, OCSP_BASIC_OID, oidOcspType, "OCSP_basic", + "Basic OCSP Response"}, + { OCSP_NONCE_OID, OCSP_NONCE_OID, oidOcspType, "OCSP_nonce", + "OCSP Nonce"}, #endif /* HAVE_OCSP */ #ifndef NO_CERTS /* oidCertExtType */ - { BASIC_CA_OID, BASIC_CA_OID, oidCertExtType, "X509 basic ca" }, - { ALT_NAMES_OID, ALT_NAMES_OID, oidCertExtType, "X509 alt names" }, - { CRL_DIST_OID, CRL_DIST_OID, oidCertExtType, "X509 crl" }, - { AUTH_INFO_OID, AUTH_INFO_OID, oidCertExtType, "X509 auth info" }, - { AUTH_KEY_OID, AUTH_KEY_OID, oidCertExtType, "X509 auth key" }, - { SUBJ_KEY_OID, SUBJ_KEY_OID, oidCertExtType, "X509 subject key" }, - { KEY_USAGE_OID, KEY_USAGE_OID, oidCertExtType, "X509 key usage" }, - { INHIBIT_ANY_OID, INHIBIT_ANY_OID, oidCertExtType, - "X509 inhibit any" }, - { NID_key_usage, KEY_USAGE_OID, oidCertExtType, - "X509 key usage" }, + { NID_basic_constraints, BASIC_CA_OID, oidCertExtType, "X509 basic ca", + "X509v3 Basic Constraints"}, + { NID_subject_alt_name, ALT_NAMES_OID, oidCertExtType, "X509 alt names", + "X509v3 Subject Alternative Name"}, + { CRL_DIST_OID, CRL_DIST_OID, oidCertExtType, "X509 crl", + "X509v3 CRL Distribution Points"}, + { NID_info_access, AUTH_INFO_OID, oidCertExtType, "X509 auth info", + "Authority Information Access"}, + { NID_authority_key_identifier, AUTH_KEY_OID, oidCertExtType, + "X509 auth key", "X509v3 Authority Key Identifier"}, + { NID_subject_key_identifier, SUBJ_KEY_OID, oidCertExtType, + "X509 subject key", "X509v3 Subject Key Identifier"}, + { NID_key_usage, KEY_USAGE_OID, oidCertExtType, "X509 key usage", + "X509v3 Key Usage"}, + { NID_inhibit_any_policy, INHIBIT_ANY_OID, oidCertExtType, + "X509 inhibit any", "X509v3 Inhibit Any Policy"}, + { NID_ext_key_usage, KEY_USAGE_OID, oidCertExtType, + "X509 ext key usage", "X509v3 Extended Key Usage"}, { NID_name_constraints, NAME_CONS_OID, oidCertExtType, - "X509 name constraints" }, + "X509 name constraints", "X509v3 Name Constraints"}, { NID_certificate_policies, CERT_POLICY_OID, oidCertExtType, - "X509 certificate policies" }, + "X509 certificate policies", "X509v3 Certificate Policies"}, /* oidCertAuthInfoType */ - { AIA_OCSP_OID, AIA_OCSP_OID, oidCertAuthInfoType, "Cert Auth OCSP" }, + { AIA_OCSP_OID, AIA_OCSP_OID, oidCertAuthInfoType, "Cert Auth OCSP", + "Authority Information Access"}, { AIA_CA_ISSUER_OID, AIA_CA_ISSUER_OID, oidCertAuthInfoType, - "Cert Auth CA Issuer" }, + "Cert Auth CA Issuer", "CA Issuers"}, /* oidCertPolicyType */ - { NID_any_policy, CP_ANY_OID, oidCertPolicyType, "Cert any policy" }, + { NID_any_policy, CP_ANY_OID, oidCertPolicyType, "Cert any policy", + "X509v3 Any Policy"}, /* oidCertAltNameType */ - { NID_hw_name_oid, HW_NAME_OID, oidCertAltNameType, "Hardware name" }, + { NID_hw_name_oid, HW_NAME_OID, oidCertAltNameType, "Hardware name",""}, /* oidCertKeyUseType */ { NID_anyExtendedKeyUsage, EKU_ANY_OID, oidCertKeyUseType, - "Cert any extended key" }, + "Cert any extended key", "Any Extended Key Usage"}, { EKU_SERVER_AUTH_OID, EKU_SERVER_AUTH_OID, oidCertKeyUseType, - "Cert server auth key" }, + "Cert server auth key", "TLS Web Server Authentication"}, { EKU_CLIENT_AUTH_OID, EKU_CLIENT_AUTH_OID, oidCertKeyUseType, - "Cert client auth key" }, + "Cert client auth key", "TLS Web Client Authentication"}, { EKU_OCSP_SIGN_OID, EKU_OCSP_SIGN_OID, oidCertKeyUseType, - "Cert OCSP sign key" }, + "Cert OCSP sign key", "OCSP Signing"}, /* oidCertNameType */ - { NID_commonName, NID_commonName, oidCertNameType, "commonName" }, - { NID_surname, NID_surname, oidCertNameType, "surname" }, - { NID_serialNumber, NID_serialNumber, oidCertNameType, "serialNumber" }, - { NID_countryName, NID_countryName, oidCertNameType, "countryName" }, - { NID_localityName, NID_localityName, oidCertNameType, "localityName" }, + { NID_commonName, NID_commonName, oidCertNameType, "commonName", + "commonName"}, + { NID_surname, NID_surname, oidCertNameType, "surname", "surname"}, + { NID_serialNumber, NID_serialNumber, oidCertNameType, "serialNumber", + "serialNumber"}, + { NID_countryName, NID_countryName, oidCertNameType, "countryName", + "countryName"}, + { NID_localityName, NID_localityName, oidCertNameType, "localityName", + "localityName"}, { NID_stateOrProvinceName, NID_stateOrProvinceName, oidCertNameType, - "stateOrProvinceName" }, + "stateOrProvinceName", "stateOrProvinceName"}, { NID_organizationName, NID_organizationName, oidCertNameType, - "organizationName" }, + "organizationName", "organizationName"}, { NID_organizationalUnitName, NID_organizationalUnitName, - oidCertNameType, "organizationalUnitName" }, - { NID_emailAddress, NID_emailAddress, oidCertNameType, "emailAddress" }, + oidCertNameType, "organizationalUnitName", "organizationUnitName"}, + { NID_emailAddress, NID_emailAddress, oidCertNameType, "emailAddress", + "emailAddress"}, #endif - #ifndef NO_PWDBASED /* oidKdfType */ - { PBKDF2_OID, PBKDF2_OID, oidKdfType, "PBKDFv2" }, + { PBKDF2_OID, PBKDF2_OID, oidKdfType, "PBKDFv2", "PBKDF2"}, /* oidPBEType */ { PBE_SHA1_RC4_128, PBE_SHA1_RC4_128, oidPBEType, - "PBE shaWithRC4-128" }, - { PBE_SHA1_DES, PBE_SHA1_DES, oidPBEType, "PBE shaWithDES" }, - { PBE_SHA1_DES3, PBE_SHA1_DES3, oidPBEType, "PBE shaWithDES3" }, + "PBE shaWithRC4-128", "pbeWithSHA1And128BitRC4"}, + { PBE_SHA1_DES, PBE_SHA1_DES, oidPBEType, "PBE shaWithDES", + "pbeWithSHA1AndDES-CBC"}, + { PBE_SHA1_DES3, PBE_SHA1_DES3, oidPBEType, "PBE shaWithDES3", + "pbeWithSHA1And3-KeyTripleDES-CBC"}, #endif /* oidKeyWrapType */ #ifdef WOLFSSL_AES_128 - { AES128_WRAP, AES128_WRAP, oidKeyWrapType, "AES-128 wrap" }, + { AES128_WRAP, AES128_WRAP, oidKeyWrapType, "AES-128 wrap", ""}, #endif #ifdef WOLFSSL_AES_192 - { AES192_WRAP, AES192_WRAP, oidKeyWrapType, "AES-192 wrap" }, + { AES192_WRAP, AES192_WRAP, oidKeyWrapType, "AES-192 wrap", ""}, #endif #ifdef WOLFSSL_AES_256 - { AES256_WRAP, AES256_WRAP, oidKeyWrapType, "AES-256 wrap" }, + { AES256_WRAP, AES256_WRAP, oidKeyWrapType, "AES-256 wrap", ""}, #endif #ifndef NO_PKCS7 @@ -34556,30 +36923,43 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) /* oidCmsKeyAgreeType */ #ifndef NO_SHA { dhSinglePass_stdDH_sha1kdf_scheme, dhSinglePass_stdDH_sha1kdf_scheme, - oidCmsKeyAgreeType, "DH-SHA kdf" }, + oidCmsKeyAgreeType, "DH-SHA kdf", ""}, #endif #ifdef WOLFSSL_SHA224 { dhSinglePass_stdDH_sha224kdf_scheme, dhSinglePass_stdDH_sha224kdf_scheme, oidCmsKeyAgreeType, - "DH-SHA224 kdf" }, + "DH-SHA224 kdf", ""}, #endif #ifndef NO_SHA256 { dhSinglePass_stdDH_sha256kdf_scheme, dhSinglePass_stdDH_sha256kdf_scheme, oidCmsKeyAgreeType, - "DH-SHA256 kdf" }, + "DH-SHA256 kdf", ""}, #endif #ifdef WOLFSSL_SHA384 { dhSinglePass_stdDH_sha384kdf_scheme, dhSinglePass_stdDH_sha384kdf_scheme, oidCmsKeyAgreeType, - "DH-SHA384 kdf" }, + "DH-SHA384 kdf", ""}, #endif #ifdef WOLFSSL_SHA512 { dhSinglePass_stdDH_sha512kdf_scheme, dhSinglePass_stdDH_sha512kdf_scheme, oidCmsKeyAgreeType, - "DH-SHA512 kdf" }, + "DH-SHA512 kdf", ""}, #endif #endif #endif + #if defined(WOLFSSL_APACHE_HTTPD) + /* "1.3.6.1.5.5.7.8.7" */ + { NID_id_on_dnsSRV, NID_id_on_dnsSRV, oidCertNameType, + WOLFSSL_SN_DNS_SRV, WOLFSSL_LN_DNS_SRV }, + + /* "1.3.6.1.4.1.311.20.2.3" */ + { NID_ms_upn, WOLFSSL_MS_UPN_SUM, oidCertExtType, WOLFSSL_SN_MS_UPN, + WOLFSSL_LN_MS_UPN }, + + /* "1.3.6.1.5.5.7.1.24" */ + { NID_tlsfeature, WOLFSSL_TLS_FEATURE_SUM, oidTlsExtType, + WOLFSSL_SN_TLS_FEATURE, WOLFSSL_LN_TLS_FEATURE }, + #endif }; #define WOLFSSL_OBJECT_INFO_SZ \ @@ -34596,6 +36976,7 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) size_t fieldSz; (void)type; + WOLFSSL_ENTER("wolfSSL_X509_NAME_add_entry_by_txt"); if (name == NULL || field == NULL) return WOLFSSL_FAILURE; @@ -35375,28 +37756,47 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) return oid2nid(oid, o->grp); } -#ifndef NO_WOLFSSL_STUB + /* Returns the long name that corresponds with an ASN1_OBJECT nid value. + * n : NID value of ASN1_OBJECT to search */ char * wolfSSL_OBJ_nid2ln(int n) { - (void)n; + int i; WOLFSSL_ENTER("wolfSSL_OBJ_nid2ln"); - WOLFSSL_STUB("OBJ_nid2ln"); + for (i = 0; i < (int)WOLFSSL_OBJECT_INFO_SZ; i++) { + if (wolfssl_object_info[i].nid == n) + return (char*)wolfssl_object_info[i].lName; + } + + WOLFSSL_MSG("NID not found in table"); return NULL; } -#endif + + /* compares two objects, return 0 if equal */ + int wolfSSL_OBJ_cmp(const WOLFSSL_ASN1_OBJECT* a, + const WOLFSSL_ASN1_OBJECT* b) + { + WOLFSSL_ENTER("wolfSSL_OBJ_cmp"); + + if (a != NULL && b != NULL && + a->obj != NULL && b->obj != NULL && + a->objSz == b->objSz) { + return XMEMCMP(a->obj, b->obj, a->objSz); + } + + return WOLFSSL_FATAL_ERROR; + } #ifdef WOLFSSL_CERT_EXT /* Gets the NID value that is related to the OID string passed in. Example * string would be "2.5.29.14" for subject key ID. * - * @TODO does not handle short names yet - * * returns NID value on success and NID_undef on error */ int wolfSSL_OBJ_txt2nid(const char* s) { int ret; + unsigned int i, sum = 0; unsigned int outSz = MAX_OID_SZ; unsigned char out[MAX_OID_SZ]; @@ -35408,34 +37808,107 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) ret = EncodePolicyOID(out, &outSz, s, NULL); if (ret == 0) { - unsigned int i, sum = 0; - /* sum OID */ for (i = 0; i < outSz; i++) { sum += out[i]; } + } - /* get the group that the OID's sum is in - * @TODO possible conflict with multiples */ - for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++) { - if (wolfssl_object_info[i].id == (int)sum) { - return wolfssl_object_info[i].nid; - } + /* get the group that the OID's sum is in + * @TODO possible conflict with multiples */ + for (i = 0; i < WOLFSSL_OBJECT_INFO_SZ; i++) { + int len; + if (ret == 0) { + if (wolfssl_object_info[i].id == (int)sum) { + return wolfssl_object_info[i].nid; + } + } + + /* try as a short name */ + len = (int)XSTRLEN(s); + if (XSTRNCMP(wolfssl_object_info[i].sName, s, len) == 0) { + return wolfssl_object_info[i].nid; + } + + /* try as a long name */ + if (XSTRNCMP(wolfssl_object_info[i].lName, s, len) == 0) { + return wolfssl_object_info[i].nid; } } + return NID_undef; } #endif /* WOLFSSL_CERT_EXT */ + /* Creates new ASN1_OBJECT from short name, long name, or text + * representation of oid. If no_name is 0, then short name, long name, and + * numerical value of oid are interpreted. If no_name is 1, then only the + * numerical value of the oid is interpreted. + * + * Returns pointer to ASN1_OBJECT on success, or NULL on error. + */ +#if defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_CERT_GEN) + WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_txt2obj(const char* s, int no_name) + { + int len, i, ret; + int nid = NID_undef; + unsigned int outSz = MAX_OID_SZ; + unsigned char out[MAX_OID_SZ]; + unsigned int sum = 0; - /* compatibility function. It's intended use is to remove OID's from an - * internal table that have been added with OBJ_create. wolfSSL manages it's - * own interenal OID values and does not currently support OBJ_create. */ + WOLFSSL_ENTER("wolfSSL_OBJ_txt2nid"); + + if (s == NULL) + return NULL; + + /* If s is numerical value, try to sum oid */ + ret = EncodePolicyOID(out, &outSz, s, NULL); + if (ret == 0) { + for (i = 0; i < (int)outSz; i++) { + sum += out[i]; + } + } + + len = (int)XSTRLEN(s); + + /* TODO: update short names in wolfssl_object_info and check OID sums + are correct */ + for (i = 0; i < (int)WOLFSSL_OBJECT_INFO_SZ; i++) { + /* Short name, long name, and numerical value are interpreted */ + if (((XSTRNCMP(s, wolfssl_object_info[i].sName, len) == 0) || + (XSTRNCMP(s, wolfssl_object_info[i].lName, len) == 0) || + (wolfssl_object_info[i].id == (int)sum)) && no_name == 0) + nid = wolfssl_object_info[i].nid; + /* Only numerical value is interpreted */ + else if (wolfssl_object_info[i].id == (int)sum && no_name == 1) + nid = wolfssl_object_info[i].nid; + } + + if (nid != NID_undef) + return wolfSSL_OBJ_nid2obj(nid); + + return NULL; + } +#endif + + /* compatibility function. Its intended use is to remove OID's from an + * internal table that have been added with OBJ_create. wolfSSL manages its + * own internal OID values and does not currently support OBJ_create. */ void wolfSSL_OBJ_cleanup(void) { WOLFSSL_ENTER("wolfSSL_OBJ_cleanup()"); } + #ifndef NO_WOLFSSL_STUB + int wolfSSL_OBJ_create(const char *oid, const char *sn, const char *ln) + { + (void)oid; + (void)sn; + (void)ln; + WOLFSSL_STUB("wolfSSL_OBJ_create"); + return WOLFSSL_FAILURE; + } + #endif #ifndef NO_WOLFSSL_STUB void wolfSSL_set_verify_depth(WOLFSSL *ssl, int depth) { @@ -35476,12 +37949,12 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) { case ASN_COMMON_NAME: sz = name->fullName.cnLen; - pt = &name->fullName.fullName[name->fullName.cnIdx], + pt = &name->fullName.fullName[name->fullName.cnIdx]; name->cnEntry.nid = name->fullName.cnNid; break; case ASN_COUNTRY_NAME: sz = name->fullName.cLen; - pt = &name->fullName.fullName[name->fullName.cIdx], + pt = &name->fullName.fullName[name->fullName.cIdx]; name->cnEntry.nid = name->fullName.cNid; break; case ASN_LOCALITY_NAME: @@ -35603,14 +38076,6 @@ void* wolfSSL_GetDhAgreeCtx(WOLFSSL* ssl) return NULL; } - #ifndef NO_WOLFSSL_STUB - void wolfSSL_sk_X509_NAME_pop_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, void f (WOLFSSL_X509_NAME*)){ - (void) sk; - (void) f; - WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_pop_free"); - WOLFSSL_STUB("sk_X509_NAME_pop_free"); - } - #endif #ifndef NO_WOLFSSL_STUB int wolfSSL_X509_check_private_key(WOLFSSL_X509 *x509, WOLFSSL_EVP_PKEY *key){ (void) x509; @@ -36025,6 +38490,28 @@ WOLFSSL_BIO *wolfSSL_BIO_new_file(const char *filename, const char *mode) #endif /* NO_FILESYSTEM */ } +#ifndef NO_FILESYSTEM +WOLFSSL_BIO* wolfSSL_BIO_new_fp(XFILE fp, int close_flag) +{ + WOLFSSL_BIO* bio; + + WOLFSSL_ENTER("wolfSSL_BIO_new_fp"); + + bio = wolfSSL_BIO_new(wolfSSL_BIO_s_file()); + if (bio == NULL) { + return bio; + } + + if (wolfSSL_BIO_set_fp(bio, fp, close_flag) != WOLFSSL_SUCCESS) { + wolfSSL_BIO_free(bio); + bio = NULL; + } + + /* file is closed when BIO is free'd or by user depending on flag */ + return bio; +} +#endif + #ifndef NO_DH WOLFSSL_DH *wolfSSL_PEM_read_bio_DHparams(WOLFSSL_BIO *bio, WOLFSSL_DH **x, @@ -36533,6 +39020,37 @@ int wolfSSL_get_state(const WOLFSSL* ssl) #if defined(OPENSSL_ALL) || defined(WOLFSSL_ASIO) +#ifndef NO_WOLFSSL_STUB +long wolfSSL_ctrl(WOLFSSL* ssl, int cmd, long opt, void* pt) +{ + WOLFSSL_STUB("SSL_ctrl"); + (void)ssl; + (void)cmd; + (void)opt; + (void)pt; + return WOLFSSL_FAILURE; +} +#endif + +#ifndef NO_WOLFSSL_STUB +long wolfSSL_CTX_ctrl(WOLFSSL_CTX* ctx, int cmd, long opt, void* pt) +{ + WOLFSSL_STUB("SSL_CTX_ctrl"); + (void)ctx; + (void)cmd; + (void)opt; + (void)pt; + return WOLFSSL_FAILURE; +} +#endif + +#ifndef NO_WOLFSSL_STUB +long wolfSSL_CTX_clear_extra_chain_certs(WOLFSSL_CTX* ctx) +{ + return wolfSSL_CTX_ctrl(ctx, SSL_CTRL_CLEAR_EXTRA_CHAIN_CERTS, 0l, NULL); +} +#endif + /* Returns the verifyCallback from the ssl structure if successful. Returns NULL otherwise. */ VerifyCallback wolfSSL_get_verify_callback(WOLFSSL* ssl) @@ -37084,15 +39602,6 @@ int wolfSSL_CIPHER_get_bits(const WOLFSSL_CIPHER *c, int *alg_bits) return ret; } -int wolfSSL_sk_X509_NAME_num(const WOLF_STACK_OF(WOLFSSL_X509_NAME) *s) -{ - WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_num"); - - if (s == NULL) - return -1; - return (int)s->num; -} - int wolfSSL_sk_X509_num(const WOLF_STACK_OF(WOLFSSL_X509) *s) { WOLFSSL_ENTER("wolfSSL_sk_X509_num"); @@ -37102,6 +39611,438 @@ int wolfSSL_sk_X509_num(const WOLF_STACK_OF(WOLFSSL_X509) *s) return (int)s->num; } +#if defined(OPENSSL_ALL) +WOLFSSL_X509_INFO* wolfSSL_X509_INFO_new(void) +{ + WOLFSSL_X509_INFO* info; + info = (WOLFSSL_X509_INFO*)XMALLOC(sizeof(WOLFSSL_X509_INFO), NULL, + DYNAMIC_TYPE_X509); + if (info) { + XMEMSET(info, 0, sizeof(*info)); + } + return info; +} + +void wolfSSL_X509_INFO_free(WOLFSSL_X509_INFO* info) +{ + if (info == NULL) + return; + + if (info->x509) { + wolfSSL_X509_free(info->x509); + info->x509 = NULL; + } + wolfSSL_X509_PKEY_free(info->x_pkey); + info->x_pkey = NULL; + + XFREE(info, NULL, DYNAMIC_TYPE_X509); +} +#endif + +WOLFSSL_STACK* wolfSSL_sk_X509_INFO_new_null(void) +{ + return wolfSSL_sk_new_node(NULL); +} + + +/* returns value less than 0 on fail to match + * On a successful match the priority level found is returned + */ +int wolfSSL_sk_SSL_CIPHER_find( + WOLF_STACK_OF(WOLFSSL_CIPHER)* sk, const WOLFSSL_CIPHER* toFind) +{ + WOLFSSL_STACK* next; + int i, sz; + + if (sk == NULL || toFind == NULL) { + return WOLFSSL_FATAL_ERROR; + } + + sz = wolfSSL_sk_SSL_CIPHER_num(sk); + next = sk; + for (i = 0; i < sz && next != NULL; i++) { + if (next->data.cipher.cipherSuite0 == toFind->cipherSuite0 && + next->data.cipher.cipherSuite == toFind->cipherSuite) { + return sz - i; /* reverse because stack pushed highest on first */ + } + next = next->next; + } + return WOLFSSL_FATAL_ERROR; +} + + +/* copies over data of "in" to "out" */ +static void wolfSSL_CIPHER_copy(WOLFSSL_CIPHER* in, WOLFSSL_CIPHER* out) +{ + if (in == NULL || out == NULL) + return; + + out->cipherSuite = in->cipherSuite; + out->cipherSuite0 = in->cipherSuite0; +} + + +/* create duplicate of stack and return the new stack + * returns null on failure */ +WOLF_STACK_OF(WOLFSSL_CIPHER)* wolfSSL_sk_SSL_CIPHER_dup( + WOLF_STACK_OF(WOLFSSL_CIPHER)* in) +{ + WOLFSSL_STACK* current; + WOLF_STACK_OF(WOLFSSL_CIPHER)* ret = NULL; + int i, sz; + + sz = wolfSSL_sk_SSL_CIPHER_num(in); + current = in; + for (i = 0; i < sz && current != NULL; i++) { + WOLFSSL_STACK* add = wolfSSL_sk_new_node(in->heap); + if (add != NULL) { + wolfSSL_CIPHER_copy(&(current->data.cipher), &(add->data.cipher)); + add->num = i+1; + add->next = ret; + ret = add; + current = current->next; + } + } + return ret; +} + +/* nothing to do yet */ +static void wolfSSL_CIPHER_free(WOLFSSL_CIPHER* in) +{ + (void)in; +} + + +/* free's all nodes in the stack and there data */ +void wolfSSL_sk_SSL_CIPHER_free(WOLF_STACK_OF(WOLFSSL_CIPHER)* sk) +{ + WOLFSSL_STACK* current = sk; + + while (current != NULL) { + WOLFSSL_STACK* toFree = current; + current = current->next; + + wolfSSL_CIPHER_free(&(toFree->data.cipher)); + wolfSSL_sk_free_node(toFree); + } +} + + +int wolfSSL_sk_X509_INFO_num(const WOLF_STACK_OF(WOLFSSL_X509_INFO) *sk) +{ + WOLFSSL_ENTER("wolfSSL_sk_X509_INFO_num"); + + if (sk == NULL) + return -1; + return (int)sk->num; +} + +WOLFSSL_X509_INFO* wolfSSL_sk_X509_INFO_value(const WOLF_STACK_OF(WOLFSSL_X509_INFO) *sk, int i) +{ + WOLFSSL_ENTER("wolfSSL_sk_X509_INFO_value"); + + for (; sk != NULL && i > 0; i--) + sk = sk->next; + + if (i != 0 || sk == NULL) + return NULL; + return sk->data.info; +} + +WOLFSSL_X509_INFO* wolfSSL_sk_X509_INFO_pop(WOLF_STACK_OF(WOLFSSL_X509_INFO)* sk) +{ + WOLFSSL_STACK* node; + WOLFSSL_X509_INFO* info; + + if (sk == NULL) { + return NULL; + } + + node = sk->next; + info = sk->data.info; + + if (node != NULL) { /* update sk and remove node from stack */ + sk->data.info = node->data.info; + sk->next = node->next; + XFREE(node, NULL, DYNAMIC_TYPE_OPENSSL); + } + else { /* last x509 in stack */ + sk->data.info = NULL; + } + + if (sk->num > 0) { + sk->num -= 1; + } + + return info; +} + +#if defined(OPENSSL_ALL) +void wolfSSL_sk_X509_INFO_pop_free(WOLF_STACK_OF(WOLFSSL_X509_INFO)* sk, + void f (WOLFSSL_X509_INFO*)) +{ + WOLFSSL_X509_INFO* info; + WOLFSSL_ENTER("wolfSSL_sk_X509_INFO_pop_free"); + + info = wolfSSL_sk_X509_INFO_pop(sk); + if (info) { + if (f) + f(info); + else + wolfSSL_X509_INFO_free(info); + } + wolfSSL_sk_free_node(sk); +} + +void wolfSSL_sk_X509_INFO_free(WOLF_STACK_OF(WOLFSSL_X509_INFO) *sk) +{ + WOLFSSL_STACK* node; + + if (sk == NULL) { + return; + } + + /* parse through stack freeing each node */ + node = sk->next; + while (sk->num > 1) { + WOLFSSL_STACK* tmp = node; + node = node->next; + + wolfSSL_X509_INFO_free(tmp->data.info); + tmp->data.info = NULL; + + XFREE(tmp, NULL, DYNAMIC_TYPE_OPENSSL); + sk->num -= 1; + } + + /* free head of stack */ + if (sk->num == 1) { + wolfSSL_X509_INFO_free(sk->data.info); + sk->data.info = NULL; + } + XFREE(sk, NULL, DYNAMIC_TYPE_OPENSSL); +} + + +/* Adds the WOLFSSL_X509_INFO to the stack "sk". "sk" takes control of "in" and + * tries to free it when the stack is free'd. + * + * return 1 on success 0 on fail + */ +int wolfSSL_sk_X509_INFO_push(WOLF_STACK_OF(WOLFSSL_X509_INFO)* sk, + WOLFSSL_X509_INFO* in) +{ + WOLFSSL_STACK* node; + + if (sk == NULL || in == NULL) { + return WOLFSSL_FAILURE; + } + + /* no previous values in stack */ + if (sk->data.info == NULL) { + sk->data.info = in; + sk->num += 1; + return WOLFSSL_SUCCESS; + } + + /* stack already has value(s) create a new node and add more */ + node = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_X509); + if (node == NULL) { + WOLFSSL_MSG("Memory error"); + return WOLFSSL_FAILURE; + } + XMEMSET(node, 0, sizeof(WOLFSSL_STACK)); + + /* push new obj onto head of stack */ + node->data.info = sk->data.info; + node->next = sk->next; + sk->next = node; + sk->data.info = in; + sk->num += 1; + + return WOLFSSL_SUCCESS; +} + + +WOLF_STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_sk_X509_NAME_new(wolf_sk_compare_cb cb) +{ + WOLFSSL_STACK* sk; + + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_new"); + + sk = wolfSSL_sk_new_node(NULL); + if (sk != NULL) { + sk->comp = cb; + } + + return sk; +} + +int wolfSSL_sk_X509_NAME_push(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, WOLFSSL_X509_NAME* name) +{ + WOLFSSL_STACK* node; + + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_push"); + + if (sk == NULL || name == NULL) { + return BAD_FUNC_ARG; + } + + /* no previous values in stack */ + if (sk->data.name == NULL) { + sk->data.name = name; + sk->num += 1; + return 0; + } + + /* stack already has value(s) create a new node and add more */ + node = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_OPENSSL); + if (node == NULL) { + WOLFSSL_MSG("Memory error"); + return MEMORY_E; + } + XMEMSET(node, 0, sizeof(WOLFSSL_STACK)); + + /* push new obj onto head of stack */ + node->data.name = sk->data.name; + node->next = sk->next; + sk->type = STACK_TYPE_X509_NAME; + sk->next = node; + sk->data.name = name; + sk->num += 1; + + return 0; +} + +/* return index of found, or negative to indicate not found */ +int wolfSSL_sk_X509_NAME_find(const WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, WOLFSSL_X509_NAME* name) +{ + int i; + + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_find"); + + if (sk == NULL) + return BAD_FUNC_ARG; + + for (i=0; sk != NULL; i++, sk = sk->next) { + if (sk->data.name == name) { + return i; + } + } + + return -1; +} + +int wolfSSL_sk_X509_NAME_set_cmp_func(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, wolf_sk_compare_cb cb) +{ + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_set_cmp_func"); + + if (sk == NULL) + return BAD_FUNC_ARG; + + sk->comp = cb; + return 0; +} +#endif /* OPENSSL_ALL */ + +int wolfSSL_sk_X509_NAME_num(const WOLF_STACK_OF(WOLFSSL_X509_NAME) *sk) +{ + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_num"); + + if (sk == NULL) + return BAD_FUNC_ARG; + + return (int)sk->num; +} + +/* Getter function for WOLFSSL_X509_NAME pointer + * + * sk is the stack to retrieve pointer from + * i is the index value in stack + * + * returns a pointer to a WOLFSSL_X509_NAME structure on success and NULL on + * fail + */ +WOLFSSL_X509_NAME* wolfSSL_sk_X509_NAME_value(const STACK_OF(WOLFSSL_X509_NAME)* sk, int i) +{ + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_value"); + + for (; sk != NULL && i > 0; i--) { + sk = sk->next; + } + + if (i != 0 || sk == NULL) + return NULL; + + return sk->data.name; +} + +WOLFSSL_X509_NAME* wolfSSL_sk_X509_NAME_pop(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk) +{ + WOLFSSL_STACK* node; + WOLFSSL_X509_NAME* name; + + if (sk == NULL) { + return NULL; + } + + node = sk->next; + name = sk->data.name; + + if (node != NULL) { /* update sk and remove node from stack */ + sk->data.name = node->data.name; + sk->next = node->next; + XFREE(node, NULL, DYNAMIC_TYPE_OPENSSL); + } + else { /* last x509 in stack */ + sk->data.name = NULL; + } + + if (sk->num > 0) { + sk->num -= 1; + } + + return name; +} + +void wolfSSL_sk_X509_NAME_pop_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, + void f (WOLFSSL_X509_NAME*)) +{ + WOLFSSL_X509_NAME* name; + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_pop_free"); + + name = wolfSSL_sk_X509_NAME_pop(sk); + if (name) { + if (f) + f(name); + else + wolfSSL_X509_NAME_free(name); + } +} + +/* Free only the sk structure */ +void wolfSSL_sk_X509_NAME_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk) +{ + WOLFSSL_STACK* node; + WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_free"); + + if (sk == NULL) + return; + + node = sk->next; + while (sk->num > 1) { + WOLFSSL_STACK* tmp = node; + node = node->next; + XFREE(tmp, NULL, DYNAMIC_TYPE_OPENSSL); + sk->num -= 1; + } + + XFREE(sk, sk->heap, DYNAMIC_TYPE_OPENSSL); +} + + int wolfSSL_X509_NAME_print_ex(WOLFSSL_BIO* bio, WOLFSSL_X509_NAME* name, int indent, unsigned long flags) { @@ -37157,10 +40098,13 @@ int wolfSSL_version(WOLFSSL* ssl) case SSLv3_MINOR : return SSL3_VERSION; case TLSv1_MINOR : - case TLSv1_1_MINOR : - case TLSv1_2_MINOR : - case TLSv1_3_MINOR : return TLS1_VERSION; + case TLSv1_1_MINOR : + return TLS1_1_VERSION; + case TLSv1_2_MINOR : + return TLS1_2_VERSION; + case TLSv1_3_MINOR : + return TLS1_3_VERSION; default: return WOLFSSL_FAILURE; } @@ -37168,8 +40112,9 @@ int wolfSSL_version(WOLFSSL* ssl) else if (ssl->version.major == DTLS_MAJOR) { switch (ssl->version.minor) { case DTLS_MINOR : - case DTLSv1_2_MINOR : return DTLS1_VERSION; + case DTLSv1_2_MINOR : + return DTLS1_2_VERSION; default: return WOLFSSL_FAILURE; } @@ -37240,16 +40185,19 @@ int wolfSSL_CTX_set_tlsext_servername_callback(WOLFSSL_CTX* ctx, WOLFSSL_ENTER("wolfSSL_CTX_set_tlsext_servername_callback"); if (ctx) { ctx->sniRecvCb = cb; - return 1; + return WOLFSSL_SUCCESS; } - return 0; + return WOLFSSL_FAILURE; } -void wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX* ctx, void* arg) +int wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX* ctx, void* arg) { WOLFSSL_ENTER("wolfSSL_CTX_set_servername_arg"); - if (ctx) + if (ctx) { ctx->sniRecvCbArg = arg; + return WOLFSSL_SUCCESS; + } + return WOLFSSL_FAILURE; } void wolfSSL_ERR_load_BIO_strings(void) { @@ -37338,8 +40286,188 @@ const byte* wolfSSL_SESSION_get_id(WOLFSSL_SESSION* sess, unsigned int* idLen) *idLen = sess->sessionIDSz; return sess->sessionID; } + +#if defined(SESSION_CERTS) || (defined(WOLFSSL_TLS13) && \ + defined(HAVE_SESSION_TICKET)) +/* returns a pointer to the protocol used by the session */ +static const char* wolfSSL_SESSION_get_protocol(const WOLFSSL_SESSION* in) +{ + return wolfSSL_internal_get_version((ProtocolVersion*)&in->version); +} #endif + +#if (defined(HAVE_SESSION_TICKET) || defined(SESSION_CERTS)) && \ + !defined(NO_FILESYSTEM) +/* returns true (non 0) if the session has EMS (extended master secret) */ +static int wolfSSL_SESSION_haveEMS(const WOLFSSL_SESSION* in) +{ + if (in == NULL) + return 0; + return in->haveEMS; +} + +#if defined(HAVE_SESSION_TICKET) +/* prints out the ticket to bio passed in + * return WOLFSSL_SUCCESS on success + */ +static int wolfSSL_SESSION_print_ticket(WOLFSSL_BIO* bio, + const WOLFSSL_SESSION* in, const char* tab) +{ + unsigned short i, j, z, sz; + short tag = 0; + byte* pt; + + + if (in == NULL || bio == NULL) { + return BAD_FUNC_ARG; + } + + sz = in->ticketLen; + pt = in->ticket; + + if (wolfSSL_BIO_printf(bio, "%s\n", (sz == 0)? " NONE": "") <= 0) + return WOLFSSL_FAILURE; + + for (i = 0; i < sz;) { + char asc[16]; + + if (sz - i < 16) { + if (wolfSSL_BIO_printf(bio, "%s%04X -", tab, tag + (sz - i)) <= 0) + return WOLFSSL_FAILURE; + } + else { + if (wolfSSL_BIO_printf(bio, "%s%04X -", tab, tag) <= 0) + return WOLFSSL_FAILURE; + } + for (j = 0; i < sz && j < 8; j++,i++) { + asc[j] = ((pt[i])&0x6f)>='A'?((pt[i])&0x6f):'.'; + if (wolfSSL_BIO_printf(bio, " %02X", pt[i]) <= 0) + return WOLFSSL_FAILURE; + } + + if (i < sz) { + asc[j] = ((pt[i])&0x6f)>='A'?((pt[i])&0x6f):'.'; + if (wolfSSL_BIO_printf(bio, "-%02X", pt[i]) <= 0) + return WOLFSSL_FAILURE; + j++; + i++; + } + + for (; i < sz && j < 16; j++,i++) { + asc[j] = ((pt[i])&0x6f)>='A'?((pt[i])&0x6f):'.'; + if (wolfSSL_BIO_printf(bio, " %02X", pt[i]) <= 0) + return WOLFSSL_FAILURE; + } + + /* pad out spacing */ + for (z = j; z < 17; z++) { + if (wolfSSL_BIO_printf(bio, " ") <= 0) + return WOLFSSL_FAILURE; + } + + for (z = 0; z < j; z++) { + if (wolfSSL_BIO_printf(bio, "%c", asc[z]) <= 0) + return WOLFSSL_FAILURE; + } + if (wolfSSL_BIO_printf(bio, "\n") <= 0) + return WOLFSSL_FAILURE; + + tag += 16; + } + return WOLFSSL_SUCCESS; +} +#endif /* HAVE_SESSION_TICKET */ + + +/* prints out the session information in human readable form + * return WOLFSSL_SUCCESS on success + */ +int wolfSSL_SESSION_print(WOLFSSL_BIO *bp, const WOLFSSL_SESSION *x) +{ + const unsigned char* pt; + unsigned char buf[SECRET_LEN]; + unsigned int sz = 0, i; + int ret; + WOLFSSL_SESSION* session = (WOLFSSL_SESSION*)x; + + if (session == NULL) { + WOLFSSL_MSG("Bad NULL argument"); + return WOLFSSL_FAILURE; + } + + if (wolfSSL_BIO_printf(bp, "%s\n", "SSL-Session:") <= 0) + return WOLFSSL_FAILURE; + +#if defined(SESSION_CERTS) || (defined(WOLFSSL_TLS13) && \ + defined(HAVE_SESSION_TICKET)) + if (wolfSSL_BIO_printf(bp, " Protocol : %s\n", + wolfSSL_SESSION_get_protocol(session)) <= 0) + return WOLFSSL_FAILURE; +#endif + + if (wolfSSL_BIO_printf(bp, " Cipher : %s\n", + wolfSSL_SESSION_CIPHER_get_name(session)) <= 0) + return WOLFSSL_FAILURE; + + pt = wolfSSL_SESSION_get_id(session, &sz); + if (wolfSSL_BIO_printf(bp, " Session-ID: ") <= 0) + return WOLFSSL_FAILURE; + + for (i = 0; i < sz; i++) { + if (wolfSSL_BIO_printf(bp, "%02X", pt[i]) <= 0) + return WOLFSSL_FAILURE; + } + if (wolfSSL_BIO_printf(bp, "\n") <= 0) + return WOLFSSL_FAILURE; + + if (wolfSSL_BIO_printf(bp, " Session-ID-ctx: \n") <= 0) + return WOLFSSL_FAILURE; + + ret = wolfSSL_SESSION_get_master_key(x, buf, sizeof(buf)); + if (wolfSSL_BIO_printf(bp, " Master-Key: ") <= 0) + return WOLFSSL_FAILURE; + + if (ret > 0) { + sz = (unsigned int)ret; + for (i = 0; i < sz; i++) { + if (wolfSSL_BIO_printf(bp, "%02X", buf[i]) <= 0) + return WOLFSSL_FAILURE; + } + } + if (wolfSSL_BIO_printf(bp, "\n") <= 0) + return WOLFSSL_FAILURE; + + /* @TODO PSK identity hint and SRP */ + + if (wolfSSL_BIO_printf(bp, " TLS session ticket:") <= 0) + return WOLFSSL_FAILURE; + +#ifdef HAVE_SESSION_TICKET + if (wolfSSL_SESSION_print_ticket(bp, x, " ") != WOLFSSL_SUCCESS) + return WOLFSSL_FAILURE; +#endif + + if (wolfSSL_BIO_printf(bp, " Start Time: %ld\n", + wolfSSL_SESSION_get_time(x)) <= 0) + return WOLFSSL_FAILURE; + + if (wolfSSL_BIO_printf(bp, " Timeout : %ld (sec)\n", + wolfSSL_SESSION_get_timeout(x)) <= 0) + return WOLFSSL_FAILURE; + + /* @TODO verify return code print */ + + if (wolfSSL_BIO_printf(bp, " Extended master secret: %s\n", + (wolfSSL_SESSION_haveEMS(session) == 0)? "no" : "yes") <= 0) + return WOLFSSL_FAILURE; + + return WOLFSSL_SUCCESS; +} +#endif /* (HAVE_SESSION_TICKET || SESSION_CERTS) && !NO_FILESYSTEM */ + +#endif /* OPENSSL_ALL || OPENSSL_EXTRA || HAVE_STUNNEL || WOLFSSL_NGINX || WOLFSSL_HAPROXY */ + #if defined(OPENSSL_ALL) || (defined(OPENSSL_EXTRA) && defined(HAVE_STUNNEL)) \ || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) @@ -37806,14 +40934,49 @@ unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, #if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) -#ifndef NO_WOLFSSL_STUB +/* returns a pointer to internal cipher suite list. Should not be free'd by + * caller. + */ WOLF_STACK_OF(WOLFSSL_CIPHER) *wolfSSL_get_ciphers_compat(const WOLFSSL *ssl) { - (void)ssl; - WOLFSSL_STUB("wolfSSL_get_ciphers_compat"); - return NULL; + WOLF_STACK_OF(WOLFSSL_CIPHER)* ret = NULL; + Suites* suites; + + WOLFSSL_ENTER("wolfSSL_get_ciphers_compat"); + if (ssl == NULL || (ssl->suites == NULL && ssl->ctx->suites == NULL)) { + return NULL; + } + + if (ssl->suites != NULL) { + suites = ssl->suites; + } + else { + suites = ssl->ctx->suites; + } + + /* check if stack needs populated */ + if (suites->stack == NULL) { + int i; + for (i = 0; i < suites->suiteSz; i+=2) { + WOLFSSL_STACK* add = wolfSSL_sk_new_node(ssl->heap); + if (add != NULL) { + add->data.cipher.cipherSuite0 = suites->suites[i]; + add->data.cipher.cipherSuite = suites->suites[i+1]; + + add->next = ret; + if (ret != NULL) { + add->num = ret->num + 1; + } + else { + add->num = 1; + } + ret = add; + } + } + suites->stack = ret; + } + return suites->stack; } -#endif #ifndef NO_WOLFSSL_STUB void wolfSSL_OPENSSL_config(char *config_name) @@ -37853,6 +41016,7 @@ void *wolfSSL_X509_get_ex_data(X509 *x509, int idx) #endif return NULL; } + int wolfSSL_X509_set_ex_data(X509 *x509, int idx, void *data) { WOLFSSL_ENTER("wolfSSL_X509_set_ex_data"); @@ -37869,6 +41033,7 @@ int wolfSSL_X509_set_ex_data(X509 *x509, int idx, void *data) #endif return WOLFSSL_FAILURE; } + int wolfSSL_X509_NAME_digest(const WOLFSSL_X509_NAME *name, const WOLFSSL_EVP_MD *type, unsigned char *md, unsigned int *len) { @@ -37994,16 +41159,33 @@ int wolfSSL_SSL_do_handshake(WOLFSSL *s) #endif } -int wolfSSL_SSL_in_init(WOLFSSL *s) +int wolfSSL_SSL_in_init(WOLFSSL *ssl) { - WOLFSSL_ENTER("wolfSSL_SSL_in_init"); + WOLFSSL_ENTER("SSL_in_init"); - if (s == NULL) + if (ssl == NULL) return WOLFSSL_FAILURE; - if (s->options.side == WOLFSSL_CLIENT_END) - return s->options.connectState < SECOND_REPLY_DONE; - return s->options.acceptState < ACCEPT_THIRD_REPLY_DONE; + if (ssl->options.side == WOLFSSL_CLIENT_END) { + return ssl->options.connectState < SECOND_REPLY_DONE; + } + return ssl->options.acceptState < ACCEPT_THIRD_REPLY_DONE; +} + +int wolfSSL_SSL_in_connect_init(WOLFSSL* ssl) +{ + WOLFSSL_ENTER("SSL_connect_init"); + + if (ssl == NULL) + return WOLFSSL_FAILURE; + + if (ssl->options.side == WOLFSSL_CLIENT_END) { + return ssl->options.connectState > CONNECT_BEGIN && + ssl->options.connectState < SECOND_REPLY_DONE; + } + + return ssl->options.acceptState > ACCEPT_BEGIN && + ssl->options.acceptState < ACCEPT_THIRD_REPLY_DONE; } #ifndef NO_SESSION_CACHE @@ -38410,24 +41592,20 @@ int wolfSSL_X509_STORE_CTX_get1_issuer(WOLFSSL_X509 **issuer, if (ca == NULL) return WOLFSSL_FAILURE; +#ifdef WOLFSSL_SIGNER_DER_CERT + /* populate issuer with Signer DER */ + *issuer = wolfSSL_X509_d2i(issuer, ca->derCert->buffer, + ca->derCert->length); + if (*issuer == NULL) + return WOLFSSL_FAILURE; +#else + /* Create an empty certificate as CA doesn't have a certificate. */ *issuer = (WOLFSSL_X509 *)XMALLOC(sizeof(WOLFSSL_X509), 0, DYNAMIC_TYPE_OPENSSL); if (*issuer == NULL) return WOLFSSL_FAILURE; - /* Create an empty certificate as CA doesn't have a certificate. */ - XMEMSET(*issuer, 0, sizeof(WOLFSSL_X509)); - (*issuer)->dynamicMemory = 1; -#ifdef WOLFSSL_SIGNER_DER_CERT - if (AllocDer(&(*issuer)->derCert, ca->derCert->length, ca->derCert->type, - NULL) == 0) { - XMEMCPY((*issuer)->derCert->buffer, ca->derCert->buffer, - ca->derCert->length); - } - else { - XFREE(*issuer, 0, DYNAMIC_TYPE_OPENSSL); - return WOLFSSL_FAILURE; - } + InitX509((*issuer), 1, NULL); #endif /* Result is ignored when passed to wolfSSL_OCSP_cert_to_id(). */ @@ -38745,6 +41923,66 @@ int wolfSSL_CTX_set_alpn_protos(WOLFSSL_CTX *ctx, const unsigned char *p, return SSL_SUCCESS; } + +#ifdef HAVE_ALPN +/* Sets the ALPN extension protos + * + * example format is + * unsigned char p[] = { + * 8, 'h', 't', 't', 'p', '/', '1', '.', '1' + * }; + * + * returns WOLFSSL_SUCCESS on success */ +int wolfSSL_set_alpn_protos(WOLFSSL* ssl, + const unsigned char* p, unsigned int p_len) +{ + WOLFSSL_BIO* bio; + char* pt; + + unsigned int sz; + unsigned int idx = 0; + int alpn_opt = WOLFSSL_ALPN_CONTINUE_ON_MISMATCH; + WOLFSSL_ENTER("wolfSSL_set_alpn_protos"); + + if (ssl == NULL || p_len <= 1) { + return WOLFSSL_FAILURE; + } + + bio = wolfSSL_BIO_new(wolfSSL_BIO_s_mem()); + if (bio == NULL) { + return WOLFSSL_FAILURE; + } + + /* convert into comma seperated list */ + while (idx < p_len - 1) { + unsigned int i; + + sz = p[idx++]; + if (idx + sz > p_len) { + WOLFSSL_MSG("Bad list format"); + wolfSSL_BIO_free(bio); + return WOLFSSL_FAILURE; + } + if (sz > 0) { + for (i = 0; i < sz; i++) { + wolfSSL_BIO_write(bio, &p[idx++], 1); + } + if (idx < p_len - 1) + wolfSSL_BIO_write(bio, ",", 1); + } + } + wolfSSL_BIO_write(bio, "\0", 1); + + /* clears out all current ALPN extensions set */ + TLSX_Remove(&ssl->extensions, TLSX_APPLICATION_LAYER_PROTOCOL, ssl->heap); + + if ((sz = wolfSSL_BIO_get_mem_data(bio, &pt)) > 0) { + wolfSSL_UseALPN(ssl, pt, sz, alpn_opt); + } + wolfSSL_BIO_free(bio); + return WOLFSSL_SUCCESS; +} +#endif /* HAVE_ALPN */ #endif #endif /* WOLFCRYPT_ONLY */ @@ -39695,6 +42933,33 @@ static int bio_get_data(WOLFSSL_BIO* bio, byte** data) return ret; } +void wolfSSL_BIO_set_init(WOLFSSL_BIO* bio, int init) +{ + WOLFSSL_STUB("wolfSSL_BIO_set_init"); + (void)bio; + (void)init; +} + +void wolfSSL_BIO_set_shutdown(WOLFSSL_BIO* bio, int shut) +{ + WOLFSSL_STUB("wolfSSL_BIO_set_shutdown"); + (void)bio; + (void)shut; + +} +int wolfSSL_BIO_get_shutdown(WOLFSSL_BIO* bio) +{ + WOLFSSL_STUB("wolfSSL_BIO_get_shutdown"); + (void)bio; + return 0; +} + +int wolfSSL_BIO_clear_retry_flags(WOLFSSL_BIO* bio) +{ + WOLFSSL_STUB("wolfSSL_BIO_clear_retry_flags"); + (void)bio; + return 0; +} /* DER data is PKCS#8 encrypted. */ WOLFSSL_EVP_PKEY* wolfSSL_d2i_PKCS8PrivateKey_bio(WOLFSSL_BIO* bio, WOLFSSL_EVP_PKEY** pkey, @@ -39794,41 +43059,14 @@ WOLFSSL_EVP_PKEY* wolfSSL_d2i_AutoPrivateKey(WOLFSSL_EVP_PKEY** pkey, return key; } -#endif - -#if defined(OPENSSL_ALL) && !defined(NO_CERTS) && defined(WOLFSSL_CERT_GEN) && \ - defined(WOLFSSL_CERT_REQ) -int wolfSSL_i2d_X509_REQ(WOLFSSL_X509* req, unsigned char** out) -{ - const unsigned char* der; - int derSz = 0; - - if (req == NULL || out == NULL) { - return BAD_FUNC_ARG; - } - - der = wolfSSL_X509_get_der(req, &derSz); - if (der == NULL) { - return MEMORY_E; - } - - if (*out == NULL) { - *out = (unsigned char*)XMALLOC(derSz, NULL, DYNAMIC_TYPE_OPENSSL); - if (*out == NULL) { - return MEMORY_E; - } - } - - XMEMCPY(*out, der, derSz); - - return derSz; -} +#ifndef NO_CERTS int wolfSSL_X509_set_subject_name(WOLFSSL_X509 *cert, WOLFSSL_X509_NAME *name) { int i; WOLFSSL_X509_NAME_ENTRY* ne; + WOLFSSL_ENTER("X509_set_subject_name"); if (cert == NULL || name == NULL) return WOLFSSL_FAILURE; @@ -39853,9 +43091,186 @@ int wolfSSL_X509_set_subject_name(WOLFSSL_X509 *cert, WOLFSSL_X509_NAME *name) return WOLFSSL_SUCCESS; } +int wolfSSL_X509_set_issuer_name(WOLFSSL_X509 *cert, WOLFSSL_X509_NAME *name) +{ + int i; + WOLFSSL_X509_NAME_ENTRY* ne; + + WOLFSSL_ENTER("X509_set_issuer_name"); + if (cert == NULL || name == NULL) + return WOLFSSL_FAILURE; + + FreeX509Name(&cert->issuer, cert->heap); + InitX509Name(&cert->issuer, 0); + if (name->dynamicName) { + cert->issuer.name = (char*)XMALLOC(name->sz, cert->heap, + DYNAMIC_TYPE_SUBJECT_CN); + if (cert->issuer.name == NULL) + return WOLFSSL_FAILURE; + } + XMEMCPY(cert->issuer.name, name->name, name->sz); + cert->issuer.sz = name->sz; + + for (i = 0; i < 10; i++) { + ne = wolfSSL_X509_NAME_get_entry(name, i); + if (ne != NULL) + wolfSSL_X509_NAME_add_entry(&cert->issuer, ne, i, 1); + } + cert->issuer.x509 = cert; + + return WOLFSSL_SUCCESS; +} +#endif /* NO_CERTS */ + +#endif /* OPENSSL_ALL */ + +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) && \ + !defined(NO_CERTS) && defined(WOLFSSL_CERT_GEN) && defined(WOLFSSL_CERT_REQ) + +int wolfSSL_X509_set_notAfter(WOLFSSL_X509* x509, const WOLFSSL_ASN1_TIME* t) +{ + unsigned int i; + unsigned char d; + + WOLFSSL_ENTER("wolfSSL_X509_set_notAfter"); + if (!x509 || !t) + return WOLFSSL_FAILURE; + + if (t->length >= MAX_DATE_SZ + 2) { + WOLFSSL_MSG("Input was larger than expected"); + return WOLFSSL_FAILURE; + } + + for (i = 0; i < MAX_DATE_SZ && (d = t->data[i]) != '\0'; i++) + x509->notAfter.data[i] = d; + + x509->notAfter.data[i] = '\0'; + x509->notAfter.length = i; + + WOLFSSL_LEAVE("wolfSSL_X509_set_notAfter", WOLFSSL_SUCCESS); + + return WOLFSSL_SUCCESS; +} + +int wolfSSL_X509_set_notBefore(WOLFSSL_X509* x509, const WOLFSSL_ASN1_TIME* t) +{ + unsigned int i; + unsigned char d; + + WOLFSSL_ENTER("wolfSSL_X509_set_notBefore"); + if (!x509 || !t) + return WOLFSSL_FAILURE; + + if (t->length >= MAX_DATE_SZ + 2) { + WOLFSSL_MSG("Input was larger than expected"); + return WOLFSSL_FAILURE; + } + + for (i = 0; i < t->length && (d = t->data[i]) != '\0'; i++) + x509->notBefore.data[i] = d; + + x509->notBefore.data[i] = '\0'; + x509->notBefore.length = i; + + return WOLFSSL_SUCCESS; +} + +int wolfSSL_X509_set_serialNumber(WOLFSSL_X509* x509, WOLFSSL_ASN1_INTEGER* s) +{ + WOLFSSL_ENTER("wolfSSL_X509_set_serialNumber"); + if (!x509 || !s || s->dataMax >= EXTERNAL_SERIAL_SIZE) + return WOLFSSL_FAILURE; + + if (s->isDynamic) + XSTRNCPY((char*)x509->serial,(char*)s->data,s->dataMax); + else + XSTRNCPY((char*)x509->serial,(char*)s->intData,s->dataMax); + + x509->serial[s->dataMax] = 0; + x509->serialSz = s->dataMax; + + return WOLFSSL_SUCCESS; +} + +int wolfSSL_X509_set_version(WOLFSSL_X509* x509, long v) +{ + WOLFSSL_ENTER("wolfSSL_X509_set_version"); + if (!x509 || v > INT_MAX) + return WOLFSSL_FAILURE; + x509->version = (int) v + 1; + + return WOLFSSL_SUCCESS; +} + +void wolfSSL_X509V3_set_ctx(WOLFSSL_X509V3_CTX* ctx, WOLFSSL_X509* issuer, + WOLFSSL_X509* subject, WOLFSSL_X509* req, WOLFSSL_X509_CRL* crl, + int flag) +{ + int ret = WOLFSSL_SUCCESS; + WOLFSSL_ENTER("wolfSSL_X509V3_set_ctx"); + if (!ctx || !ctx->x509) + return; + + /* Set parameters in ctx as long as ret == WOLFSSL_SUCCESS */ + if (issuer) + ret = wolfSSL_X509_set_issuer_name(ctx->x509,&issuer->issuer); + + if (subject && ret == WOLFSSL_SUCCESS) + ret = wolfSSL_X509_set_subject_name(ctx->x509,&subject->subject); + + if (req && ret == WOLFSSL_SUCCESS) { + WOLFSSL_MSG("req not implemented."); + } + + if (crl && ret == WOLFSSL_SUCCESS) { + WOLFSSL_MSG("crl not implemented."); + } + + if (flag && ret == WOLFSSL_SUCCESS) { + WOLFSSL_MSG("flag not implemented."); + } + + if (!ret) { + WOLFSSL_MSG("Error setting WOLFSSL_X509V3_CTX parameters."); + } +} + + +#endif /* OPENSSL_ALL || WOLFSSL_APACHE_HTTPD */ + +#if defined(OPENSSL_ALL) && !defined(NO_CERTS) && defined(WOLFSSL_CERT_GEN) && \ + defined(WOLFSSL_CERT_REQ) +int wolfSSL_i2d_X509_REQ(WOLFSSL_X509* req, unsigned char** out) +{ + const unsigned char* der; + int derSz = 0; + WOLFSSL_ENTER("wolfSSL_i2d_X509_REQ"); + + if (req == NULL || out == NULL) { + return BAD_FUNC_ARG; + } + + der = wolfSSL_X509_get_der(req, &derSz); + if (der == NULL) { + return MEMORY_E; + } + + if (*out == NULL) { + *out = (unsigned char*)XMALLOC(derSz, NULL, DYNAMIC_TYPE_OPENSSL); + if (*out == NULL) { + return MEMORY_E; + } + } + + XMEMCPY(*out, der, derSz); + + return derSz; +} + int wolfSSL_X509_set_pubkey(WOLFSSL_X509 *cert, WOLFSSL_EVP_PKEY *pkey) { byte* p; + WOLFSSL_ENTER("wolfSSL_X509_set_pubkey"); if (cert == NULL || pkey == NULL) return WOLFSSL_FAILURE; @@ -39892,188 +43307,39 @@ void wolfSSL_X509_REQ_free(WOLFSSL_X509* req) } -static int ReqCertFromX509(Cert* cert, WOLFSSL_X509* req) -{ - int ret; - - ret = CopyX509NameToCertName(&req->subject, &cert->subject); - if (ret == WOLFSSL_SUCCESS) { - cert->version = req->version; - cert->isCA = req->isCa; - if (req->subjKeyIdSz != 0) { - XMEMCPY(cert->skid, req->subjKeyId, req->subjKeyIdSz); - cert->skidSz = req->subjKeyIdSz; - } - if (req->keyUsageSet) - cert->keyUsage = req->keyUsage; - /* Extended Key Usage not supported. */ - } - - return ret; -} - int wolfSSL_X509_REQ_sign(WOLFSSL_X509 *req, WOLFSSL_EVP_PKEY *pkey, const WOLFSSL_EVP_MD *md) { - int ret; - Cert cert; byte der[2048]; int derSz = sizeof(der); - void* key = NULL; - int type = -1; - int sigType; - int hashType; -#ifndef NO_RSA - RsaKey rsa; -#endif -#ifdef HAVE_ECC - ecc_key ecc; -#endif - WC_RNG rng; - word32 idx = 0; if (req == NULL || pkey == NULL || md == NULL) return WOLFSSL_FAILURE; /* Create a Cert that has the certificate request fields. */ - if (wc_InitCert(&cert) != 0) + req->sigOID = wolfSSL_sigTypeFromPKEY((WOLFSSL_EVP_MD*)md, pkey); + if (wolfSSL_X509_make_der(req, 1, der, &derSz) != WOLFSSL_SUCCESS) { return WOLFSSL_FAILURE; - if (ReqCertFromX509(&cert, req) != WOLFSSL_SUCCESS) - return WOLFSSL_FAILURE; - - /* Convert key type and hash algorithm to a signature algorithm */ - if (wolfSSL_EVP_get_hashinfo(md, &hashType, NULL) == WOLFSSL_FAILURE) - return WOLFSSL_FAILURE; - - if (pkey->type == EVP_PKEY_RSA) { - switch (hashType) { - case WC_HASH_TYPE_SHA: - sigType = CTC_SHAwRSA; - break; - case WC_HASH_TYPE_SHA224: - sigType = CTC_SHA224wRSA; - break; - case WC_HASH_TYPE_SHA256: - sigType = CTC_SHA256wRSA; - break; - case WC_HASH_TYPE_SHA384: - sigType = CTC_SHA384wRSA; - break; - case WC_HASH_TYPE_SHA512: - sigType = CTC_SHA512wRSA; - break; - default: - return WOLFSSL_FAILURE; - } } - else if (pkey->type == EVP_PKEY_EC) { - switch (hashType) { - case WC_HASH_TYPE_SHA: - sigType = CTC_SHAwECDSA; - break; - case WC_HASH_TYPE_SHA224: - sigType = CTC_SHA224wECDSA; - break; - case WC_HASH_TYPE_SHA256: - sigType = CTC_SHA256wECDSA; - break; - case WC_HASH_TYPE_SHA384: - sigType = CTC_SHA384wECDSA; - break; - case WC_HASH_TYPE_SHA512: - sigType = CTC_SHA512wECDSA; - break; - default: - return WOLFSSL_FAILURE; - } + + if (wolfSSL_X509_resign_cert(req, 1, der, sizeof(der), derSz, + (WOLFSSL_EVP_MD*)md, pkey) <= 0) { + return WOLFSSL_FAILURE; } - else - return WOLFSSL_FAILURE; - - /* Create a public key object from requests public key. */ -#ifndef NO_RSA - if (req->pubKeyOID == RSAk) { - type = RSA_TYPE; - ret = wc_InitRsaKey(&rsa, req->heap); - if (ret != 0) - return WOLFSSL_FAILURE; - ret = wc_RsaPublicKeyDecode(req->pubKey.buffer, &idx, &rsa, - req->pubKey.length); - if (ret != 0) { - wc_FreeRsaKey(&rsa); - return WOLFSSL_FAILURE; - } - key = (void*)&rsa; - } -#endif -#ifdef HAVE_ECC - if (req->pubKeyOID == ECDSAk) { - type = ECC_TYPE; - ret = wc_ecc_init(&ecc); - if (ret != 0) - return WOLFSSL_FAILURE; - ret = wc_EccPublicKeyDecode(req->pubKey.buffer, &idx, &ecc, - req->pubKey.length); - if (ret != 0) { - wc_ecc_free(&ecc); - return WOLFSSL_FAILURE; - } - key = (void*)&ecc; - } -#endif - if (key == NULL) - return WOLFSSL_FAILURE; - - /* Make the body of the certificate request. */ - ret = wc_MakeCertReq_ex(&cert, der, derSz, type, key); - if (ret < 0) - return WOLFSSL_FAILURE; - - /* Dispose of the public key object. */ -#ifndef NO_RSA - if (req->pubKeyOID == RSAk) - wc_FreeRsaKey(&rsa); -#endif -#ifdef HAVE_ECC - if (req->pubKeyOID == ECDSAk) - wc_ecc_free(&ecc); -#endif - - idx = 0; - /* Get the private key object and type from pkey. */ -#ifndef NO_RSA - if (pkey->type == EVP_PKEY_RSA) { - type = RSA_TYPE; - key = pkey->rsa->internal; - } -#endif -#ifdef HAVE_ECC - if (pkey->type == EVP_PKEY_EC) { - type = ECC_TYPE; - key = pkey->ecc->internal; - } -#endif - - /* Sign the certificate request body. */ - ret = wc_InitRng(&rng); - if (ret != 0) - return WOLFSSL_FAILURE; - ret = wc_SignCert_ex(cert.bodySz, sigType, der, sizeof(der), type, key, - &rng); - wc_FreeRng(&rng); - if (ret < 0) - return WOLFSSL_FAILURE; - - /* Put in the new certificate request encoding into the request object. */ - FreeDer(&req->derCert); - if (AllocDer(&req->derCert, ret, CERTREQ_TYPE, NULL) != 0) - return WOLFSSL_FAILURE; - XMEMCPY(req->derCert->buffer, der, ret); - req->derCert->length = ret; - return WOLFSSL_SUCCESS; } + +#ifndef NO_WOLFSSL_STUB +int wolfSSL_X509_REQ_add_extensions(WOLFSSL_X509* req, + WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* ext) +{ + (void)req; + (void)ext; + return WOLFSSL_FATAL_ERROR; +} +#endif + int wolfSSL_X509_REQ_set_subject_name(WOLFSSL_X509 *req, WOLFSSL_X509_NAME *name) { diff --git a/src/tls.c b/src/tls.c index 3d43428f9..503057119 100644 --- a/src/tls.c +++ b/src/tls.c @@ -10949,6 +10949,36 @@ int TLSX_Parse(WOLFSSL* ssl, byte* input, word16 length, byte msgType, #ifndef NO_WOLFSSL_CLIENT + WOLFSSL_METHOD* wolfTLS_client_method(void) + { + return wolfTLS_client_method_ex(NULL); + } + WOLFSSL_METHOD* wolfTLS_client_method_ex(void* heap) + { + WOLFSSL_METHOD* method = + (WOLFSSL_METHOD*) XMALLOC(sizeof(WOLFSSL_METHOD), + heap, DYNAMIC_TYPE_METHOD); + (void)heap; + WOLFSSL_ENTER("TLS_client_method_ex"); + if (method) { + #if defined(WOLFSSL_TLS13) + InitSSL_Method(method, MakeTLSv1_3()); + #elif !defined(WOLFSSL_NO_TLS12) + InitSSL_Method(method, MakeTLSv1_2()); + #elif !defined(NO_OLD_TLS) + InitSSL_Method(method, MakeTLSv1_1()); + #elif defined(WOLFSSL_ALLOW_TLSV10) + InitSSL_Method(method, MakeTLSv1()); + #else + #error No TLS version enabled! + #endif + + method->downgrade = 1; + method->side = WOLFSSL_CLIENT_END; + } + return method; + } + #ifndef NO_OLD_TLS #ifdef WOLFSSL_ALLOW_TLSV10 WOLFSSL_METHOD* wolfTLSv1_client_method(void) @@ -11269,6 +11299,37 @@ int TLSX_Parse(WOLFSSL* ssl, byte* input, word16 length, byte msgType, #ifndef NO_WOLFSSL_SERVER + WOLFSSL_METHOD* wolfTLS_server_method(void) + { + return wolfTLS_server_method_ex(NULL); + } + + WOLFSSL_METHOD* wolfTLS_server_method_ex(void* heap) + { + WOLFSSL_METHOD* method = + (WOLFSSL_METHOD*) XMALLOC(sizeof(WOLFSSL_METHOD), + heap, DYNAMIC_TYPE_METHOD); + (void)heap; + WOLFSSL_ENTER("TLS_server_method_ex"); + if (method) { + #if defined(WOLFSSL_TLS13) + InitSSL_Method(method, MakeTLSv1_3()); + #elif !defined(WOLFSSL_NO_TLS12) + InitSSL_Method(method, MakeTLSv1_2()); + #elif !defined(NO_OLD_TLS) + InitSSL_Method(method, MakeTLSv1_1()); + #elif defined(WOLFSSL_ALLOW_TLSV10) + InitSSL_Method(method, MakeTLSv1()); + #else + #error No TLS version enabled! + #endif + + method->downgrade = 1; + method->side = WOLFSSL_SERVER_END; + } + return method; + } + #ifndef NO_OLD_TLS #ifdef WOLFSSL_ALLOW_TLSV10 WOLFSSL_METHOD* wolfTLSv1_server_method(void) diff --git a/src/tls13.c b/src/tls13.c index bca23415d..c5939b507 100644 --- a/src/tls13.c +++ b/src/tls13.c @@ -8445,6 +8445,9 @@ int wolfSSL_accept_TLSv13(WOLFSSL* ssl) switch (ssl->options.acceptState) { +#ifdef HAVE_SECURE_RENEGOTIATION + case TLS13_ACCEPT_BEGIN_RENEG: +#endif case TLS13_ACCEPT_BEGIN : /* get client_hello */ while (ssl->options.clientState < CLIENT_HELLO_COMPLETE) { diff --git a/src/wolfio.c b/src/wolfio.c index f08f392bf..45cffb1fa 100644 --- a/src/wolfio.c +++ b/src/wolfio.c @@ -125,14 +125,25 @@ int BioReceive(WOLFSSL* ssl, char* buf, int sz, void* ctx) return WOLFSSL_CBIO_ERR_GENERAL; } + if (ssl->biord->method && ssl->biord->method->custom && + ssl->biord->method->custom->readCb) { + WOLFSSL_MSG("Calling custom biord"); + recvd = ssl->biord->method->custom->readCb(ssl->biord, buf, sz); + if (recvd < 0 && recvd != WOLFSSL_CBIO_ERR_WANT_READ) + return WOLFSSL_CBIO_ERR_GENERAL; + return recvd; + } + switch (ssl->biord->type) { case WOLFSSL_BIO_MEMORY: case WOLFSSL_BIO_BIO: if (wolfSSL_BIO_ctrl_pending(ssl->biord) == 0) { + WOLFSSL_MSG("BIO want read"); return WOLFSSL_CBIO_ERR_WANT_READ; } recvd = wolfSSL_BIO_read(ssl->biord, buf, sz); if (recvd <= 0) { + WOLFSSL_MSG("BIO general error"); return WOLFSSL_CBIO_ERR_GENERAL; } break; @@ -161,11 +172,23 @@ int BioSend(WOLFSSL* ssl, char *buf, int sz, void *ctx) { int sent = WOLFSSL_CBIO_ERR_GENERAL; + WOLFSSL_ENTER("BioSend"); + if (ssl->biowr == NULL) { - WOLFSSL_MSG("WOLFSSL biowr not set\n"); + WOLFSSL_MSG("WOLFSSL biowr not set"); return WOLFSSL_CBIO_ERR_GENERAL; } + if (ssl->biowr->method && ssl->biowr->method->custom && + ssl->biowr->method->custom->writeCb) { + WOLFSSL_MSG("Calling custom biowr"); + sent = ssl->biowr->method->custom->writeCb(ssl->biowr, buf, sz); + if (sent < 0) { + return WOLFSSL_CBIO_ERR_GENERAL; + } + return sent; + } + switch (ssl->biowr->type) { case WOLFSSL_BIO_MEMORY: case WOLFSSL_BIO_BIO: diff --git a/tests/api.c b/tests/api.c index 34b2e4bfc..44879b2a6 100644 --- a/tests/api.c +++ b/tests/api.c @@ -292,8 +292,11 @@ #if (defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL) || defined(OPENSSL_ALL)) #include #ifndef NO_ASN - /* for ASN_COMMON_NAME DN_tags enum */ - #include + /* for ASN_COMMON_NAME DN_tags enum */ + #include + #endif + #ifdef HAVE_OCSP + #include #endif #endif #ifdef OPENSSL_EXTRA @@ -1599,8 +1602,12 @@ static int test_wolfSSL_SetMinVersion(void) int itr; #ifndef NO_OLD_TLS - const int versions[] = { WOLFSSL_TLSV1, WOLFSSL_TLSV1_1, - WOLFSSL_TLSV1_2}; + const int versions[] = { + #ifdef WOLFSSL_ALLOW_TLSV10 + WOLFSSL_TLSV1, + #endif + WOLFSSL_TLSV1_1, + WOLFSSL_TLSV1_2}; #elif !defined(WOLFSSL_NO_TLS12) const int versions[] = { WOLFSSL_TLSV1_2 }; #else @@ -1734,6 +1741,21 @@ static void test_wolfSSL_EC(void) } #endif +static void test_wolfSSL_PEM_read_bio_ECPKParameters(void) +{ +#if defined(HAVE_ECC) && !defined(NO_FILESYSTEM) && defined(OPENSSL_EXTRA) + EC_GROUP *group; + BIO* bio; + + AssertNotNull(bio = BIO_new(BIO_s_file())); + AssertIntEQ(BIO_read_filename(bio, eccKeyFile), WOLFSSL_SUCCESS); + AssertNotNull(group = PEM_read_bio_ECPKParameters(bio, NULL, NULL, NULL)); + AssertIntEQ(EC_GROUP_get_curve_name(group), NID_X9_62_prime256v1); + EC_GROUP_free(group); + BIO_free(bio); +#endif /* HAVE_ECC */ +} + # if defined(OPENSSL_EXTRA) static void test_wolfSSL_ECDSA_SIG(void) { @@ -4879,7 +4901,11 @@ static int test_wolfSSL_CTX_SetMinVersion(void) int itr; #ifndef NO_OLD_TLS - const int versions[] = { WOLFSSL_TLSV1, WOLFSSL_TLSV1_1, + const int versions[] = { + #ifdef WOLFSSL_ALLOW_TLSV10 + WOLFSSL_TLSV1, + #endif + WOLFSSL_TLSV1_1, WOLFSSL_TLSV1_2 }; #elif !defined(WOLFSSL_NO_TLS12) const int versions[] = { WOLFSSL_TLSV1_2 }; @@ -18824,11 +18850,13 @@ static void test_wolfSSL_ASN1_TIME_print(void) /* create a bad time and test results */ AssertNotNull(t = X509_get_notAfter(x509)); + AssertIntEQ(ASN1_TIME_check(t), WOLFSSL_SUCCESS); t->data[10] = 0; t->data[5] = 0; AssertIntNE(ASN1_TIME_print(bio, t), 1); AssertIntEQ(BIO_read(bio, buf, sizeof(buf)), 14); AssertIntEQ(XMEMCMP(buf, "Bad time value", 14), 0); + AssertIntEQ(ASN1_TIME_check(t), WOLFSSL_FAILURE); BIO_free(bio); X509_free(x509); @@ -18837,6 +18865,56 @@ static void test_wolfSSL_ASN1_TIME_print(void) #endif } +static void test_wolfSSL_ASN1_UTCTIME_print(void) +{ + #if defined(OPENSSL_EXTRA) + BIO* bio; + ASN1_UTCTIME* utc = NULL; + unsigned char buf[25]; + const char* validDate = "190424111501Z"; /* UTC = YYMMDDHHMMSSZ */ + const char* invalidDate = "190424111501X"; /* UTC = YYMMDDHHMMSSZ */ + byte* ptr1; + byte* ptr2; + + printf(testingFmt, "ASN1_UTCTIME_print()"); + + /* NULL parameter check */ + AssertNotNull(bio = BIO_new(BIO_s_mem())); + AssertIntEQ(ASN1_UTCTIME_print(bio, utc), 0); + BIO_free(bio); + + /* Valid date */ + AssertNotNull(bio = BIO_new(BIO_s_mem())); + AssertNotNull(utc = (ASN1_UTCTIME*)XMALLOC(sizeof(ASN1_UTCTIME), NULL, + DYNAMIC_TYPE_ASN1)); + ptr1 = utc->data; + *ptr1 = (byte)ASN_UTC_TIME; ptr1++; + *ptr1 = (byte)ASN_UTC_TIME_SIZE; ptr1++; + XMEMCPY(ptr1, (byte*)validDate, ASN_UTC_TIME_SIZE); + AssertIntEQ(ASN1_UTCTIME_print(bio, utc), 1); + AssertIntEQ(BIO_read(bio, buf, sizeof(buf)), 24); + AssertIntEQ(XMEMCMP(buf, "Apr 24 11:15:01 2019 GMT", sizeof(buf)-1), 0); + + XMEMSET(buf, 0, sizeof(buf)); + BIO_free(bio); + + /* Invalid format */ + AssertNotNull(bio = BIO_new(BIO_s_mem())); + ptr2 = utc->data; + *ptr2 = (byte)ASN_UTC_TIME; ptr2++; + *ptr2 = (byte)ASN_UTC_TIME_SIZE; ptr2++; + XMEMCPY(ptr2, (byte*)invalidDate, ASN_UTC_TIME_SIZE); + AssertIntEQ(ASN1_UTCTIME_print(bio, utc), 0); + AssertIntEQ(BIO_read(bio, buf, sizeof(buf)), 14); + AssertIntEQ(XMEMCMP(buf, "Bad time value", 14), 0); + + XFREE(utc, NULL, DYNAMIC_TYPE_ASN1); + BIO_free(bio); + + printf(resultFmt, passed); + #endif /* OPENSSL_EXTRA */ +} + static void test_wolfSSL_ASN1_GENERALIZEDTIME_free(void) { @@ -19139,6 +19217,7 @@ static void test_wolfSSL_PEM_PrivateKey(void) #if !defined(NO_DES3) && defined(WOLFSSL_ENCRYPTED_KEYS) && \ !defined(NO_RSA) && !defined(NO_FILESYSTEM) { + XFILE f; pem_password_cb* passwd_cb; void* passwd_cb_userdata; SSL_CTX* ctx; @@ -19164,7 +19243,9 @@ static void test_wolfSSL_PEM_PrivateKey(void) AssertNull(pkey = PEM_read_bio_PrivateKey(bio, NULL, passwd_cb, (void*)passwd)); BIO_free(bio); - AssertNotNull(bio = BIO_new_file("./certs/server-keyEnc.pem", "rb")); + + f = XFOPEN("./certs/server-keyEnc.pem", "rb"); + AssertNotNull(bio = BIO_new_fp(f, BIO_CLOSE)); /* use callback that works */ AssertNotNull(pkey = PEM_read_bio_PrivateKey(bio, NULL, passwd_cb, @@ -19928,6 +20009,59 @@ static int verify_cb(int ok, X509_STORE_CTX *ctx) #endif +static void test_wolfSSL_X509_STORE_CTX_get0_current_issuer(void) +{ +#if defined(OPENSSL_EXTRA) && !defined(NO_RSA) + #ifdef WOLFSSL_SIGNER_DER_CERT + int cmp; + #endif + X509_STORE_CTX* ctx; + X509_STORE* str; + X509* x509Ca; + X509* x509Svr; + X509* issuer; + X509_NAME* caName; + X509_NAME* issuerName; + + printf(testingFmt, "wolfSSL_X509_STORE_CTX_get0_current_issuer()"); + + AssertNotNull(ctx = X509_STORE_CTX_new()); + AssertNotNull((str = wolfSSL_X509_STORE_new())); + AssertNotNull((x509Ca = + wolfSSL_X509_load_certificate_file(caCertFile, SSL_FILETYPE_PEM))); + AssertIntEQ(X509_STORE_add_cert(str, x509Ca), SSL_SUCCESS); + AssertNotNull((x509Svr = + wolfSSL_X509_load_certificate_file(svrCertFile, SSL_FILETYPE_PEM))); + + AssertIntEQ(X509_STORE_CTX_init(ctx, str, x509Svr, NULL), SSL_SUCCESS); + + AssertNull(X509_STORE_CTX_get0_current_issuer(NULL)); + issuer = X509_STORE_CTX_get0_current_issuer(ctx); + AssertNotNull(issuer); + + caName = X509_get_subject_name(x509Ca); + AssertNotNull(caName); + issuerName = X509_get_subject_name(issuer); + #ifdef WOLFSSL_SIGNER_DER_CERT + AssertNotNull(issuerName); + cmp = X509_NAME_cmp(caName, issuerName); + AssertIntEQ(cmp, 0); + #else + /* X509_STORE_CTX_get0_current_issuer() returns empty issuer */ + AssertNull(issuerName); + #endif + + X509_free(issuer); + X509_STORE_CTX_free(ctx); + #ifdef WOLFSSL_KEEP_STORE_CERTS + X509_free(x509Svr); + #endif + X509_free(x509Ca); + + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_X509_STORE_CTX(void) { @@ -19938,7 +20072,8 @@ static void test_wolfSSL_X509_STORE_CTX(void) X509_STORE* str; X509* x509; #ifdef OPENSSL_ALL - STACK_OF(X509)* sk; + X509* x5092; + STACK_OF(X509) *sk, *sk2, *sk3; #endif printf(testingFmt, "wolfSSL_X509_STORE_CTX()"); @@ -19948,6 +20083,7 @@ static void test_wolfSSL_X509_STORE_CTX(void) wolfSSL_X509_load_certificate_file(svrCertFile, SSL_FILETYPE_PEM))); AssertIntEQ(X509_STORE_add_cert(str, x509), SSL_SUCCESS); #ifdef OPENSSL_ALL + /* sk_X509_new only in OPENSSL_ALL */ AssertNotNull(sk = sk_X509_new()); AssertIntEQ(X509_STORE_CTX_init(ctx, str, x509, sk), SSL_SUCCESS); #else @@ -19962,7 +20098,6 @@ static void test_wolfSSL_X509_STORE_CTX(void) sk_X509_free(sk); #endif #ifdef WOLFSSL_KEEP_STORE_CERTS - X509_STORE_free(str); X509_free(x509); #endif @@ -19970,6 +20105,55 @@ static void test_wolfSSL_X509_STORE_CTX(void) X509_STORE_CTX_set_verify_cb(ctx, (void *)verify_cb); X509_STORE_CTX_free(ctx); +#ifdef OPENSSL_ALL + /* test X509_STORE_CTX_get(1)_chain */ + AssertNotNull((x509 = X509_load_certificate_file(svrCertFile, + SSL_FILETYPE_PEM))); + AssertNotNull((x5092 = X509_load_certificate_file(cliCertFile, + SSL_FILETYPE_PEM))); + AssertNotNull((sk = sk_X509_new())); + AssertIntEQ(sk_X509_push(sk, x509), 1); + AssertNotNull((str = X509_STORE_new())); + AssertNotNull((ctx = X509_STORE_CTX_new())); + AssertIntEQ(X509_STORE_CTX_init(ctx, str, x5092, sk), 1); + AssertNull((sk2 = X509_STORE_CTX_get_chain(NULL))); + AssertNotNull((sk2 = X509_STORE_CTX_get_chain(ctx))); + AssertIntEQ(sk_num(sk2), 1); /* sanity, make sure chain has 1 cert */ + AssertNull((sk3 = X509_STORE_CTX_get1_chain(NULL))); + AssertNotNull((sk3 = X509_STORE_CTX_get1_chain(ctx))); + AssertIntEQ(sk_num(sk3), 1); /* sanity, make sure chain has 1 cert */ + X509_STORE_CTX_free(ctx); + sk_X509_free(sk); + #ifdef WOLFSSL_KEEP_STORE_CERTS + /* CTX certs not freed yet */ + X509_free(x5092); + #endif + /* sk2 freed as part of X509_STORE_CTX_free(), sk3 is dup so free here */ + sk_X509_free(sk3); +#endif + + /* test X509_STORE_CTX_get/set_ex_data */ + { + int i = 0, tmpData = 5; + int* tmpDataRet; + AssertNotNull(ctx = X509_STORE_CTX_new()); + #if defined(HAVE_EX_DATA) || defined(FORTRESS) + for (i = 0; i < MAX_EX_DATA; i++) { + AssertIntEQ(X509_STORE_CTX_set_ex_data(ctx, i, &tmpData), + WOLFSSL_SUCCESS); + tmpDataRet = X509_STORE_CTX_get_ex_data(ctx, i); + AssertNotNull(tmpDataRet); + AssertIntEQ(tmpData, *tmpDataRet); + } + #else + AssertIntEQ(X509_STORE_CTX_set_ex_data(ctx, i, &tmpData), + WOLFSSL_FAILURE); + tmpDataRet = (int*)X509_STORE_CTX_get_ex_data(ctx, i); + AssertNull(tmpDataRet); + #endif + X509_STORE_CTX_free(ctx); + } + printf(resultFmt, passed); #endif /* defined(OPENSSL_EXTRA) && !defined(NO_CERTS) && \ !defined(NO_FILESYSTEM) && !defined(NO_RSA) */ @@ -20111,6 +20295,31 @@ static void test_wolfSSL_X509_VERIFY_PARAM_set1_host(void) #endif /* OPENSSL_EXTRA */ } +static void test_wolfSSL_X509_STORE_CTX_get0_store(void) +{ + #if defined(OPENSSL_EXTRA) + X509_STORE* store; + X509_STORE_CTX* ctx; + X509_STORE_CTX* ctx_no_init; + + printf(testingFmt, "wolfSSL_X509_STORE_CTX_get0_store()"); + AssertNotNull((store = X509_STORE_new())); + AssertNotNull(ctx = X509_STORE_CTX_new()); + AssertNotNull(ctx_no_init = X509_STORE_CTX_new()); + AssertIntEQ(X509_STORE_CTX_init(ctx, store, NULL, NULL), SSL_SUCCESS); + + AssertNull(X509_STORE_CTX_get0_store(NULL)); + /* should return NULL if ctx has not bee initialized */ + AssertNull(X509_STORE_CTX_get0_store(ctx_no_init)); + AssertNotNull(X509_STORE_CTX_get0_store(ctx)); + + wolfSSL_X509_STORE_CTX_free(ctx); + wolfSSL_X509_STORE_CTX_free(ctx_no_init); + + printf(resultFmt, passed); + #endif /* OPENSSL_EXTRA */ +} + static void test_wolfSSL_CTX_set_client_CA_list(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_RSA) && !defined(NO_CERTS) @@ -20322,6 +20531,54 @@ static void test_wolfSSL_X509_STORE(void) return; } +static void test_wolfSSL_X509_STORE_load_locations(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) && !defined(NO_FILESYSTEM) + SSL_CTX *ctx; + X509_STORE *store; + + const char ca_file[] = "./certs/ca-cert.pem"; + const char client_pem_file[] = "./certs/client-cert.pem"; + const char client_der_file[] = "./certs/client-cert.der"; + const char ecc_file[] = "./certs/ecc-key.pem"; + const char certs_path[] = "./certs/"; + const char bad_path[] = "./bad-path/"; +#ifdef HAVE_CRL + const char crl_path[] = "./certs/crl/"; + const char crl_file[] = "./certs/crl/crl.pem"; +#endif + + printf(testingFmt, "wolfSSL_X509_STORE_load_locations"); + + AssertNotNull(ctx = SSL_CTX_new(SSLv23_server_method())); + AssertNotNull(store = SSL_CTX_get_cert_store(ctx)); + AssertIntEQ(wolfSSL_CertManagerLoadCA(store->cm, ca_file, NULL), WOLFSSL_SUCCESS); + + /* Test bad arguments */ + AssertIntEQ(X509_STORE_load_locations(NULL, ca_file, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_STORE_load_locations(store, NULL, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_STORE_load_locations(store, client_der_file, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_STORE_load_locations(store, ecc_file, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_STORE_load_locations(store, NULL, bad_path), WOLFSSL_FAILURE); + +#ifdef HAVE_CRL + /* Test with CRL */ + AssertIntEQ(X509_STORE_load_locations(store, crl_file, NULL), WOLFSSL_SUCCESS); + AssertIntEQ(X509_STORE_load_locations(store, NULL, crl_path), WOLFSSL_SUCCESS); +#endif + + /* Test with CA */ + AssertIntEQ(X509_STORE_load_locations(store, ca_file, NULL), WOLFSSL_SUCCESS); + + /* Test with client_cert and certs path */ + AssertIntEQ(X509_STORE_load_locations(store, client_pem_file, NULL), WOLFSSL_SUCCESS); + AssertIntEQ(X509_STORE_load_locations(store, NULL, certs_path), WOLFSSL_SUCCESS); + + SSL_CTX_free(ctx); + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_BN(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_ASN) @@ -20810,6 +21067,38 @@ static void test_wolfSSL_set_options(void) !defined(NO_FILESYSTEM) && !defined(NO_RSA) */ } +static void test_wolfSSL_sk_SSL_CIPHER(void) +{ + #if defined(OPENSSL_ALL) && !defined(NO_CERTS) && \ + !defined(NO_FILESYSTEM) && !defined(NO_RSA) + SSL* ssl; + SSL_CTX* ctx; + STACK_OF(SSL_CIPHER) *sk, *dup; + + printf(testingFmt, "wolfSSL_sk_SSL_CIPHER_*()"); + + AssertNotNull(ctx = SSL_CTX_new(wolfSSLv23_server_method())); + AssertTrue(SSL_CTX_use_certificate_file(ctx, svrCertFile, SSL_FILETYPE_PEM)); + AssertTrue(SSL_CTX_use_PrivateKey_file(ctx, svrKeyFile, SSL_FILETYPE_PEM)); + AssertNotNull(ssl = SSL_new(ctx)); + AssertNotNull(sk = SSL_get_ciphers(ssl)); + AssertNotNull(dup = sk_SSL_CIPHER_dup(sk)); + AssertIntGT(sk_SSL_CIPHER_num(sk), 0); + AssertIntEQ(sk_SSL_CIPHER_num(sk), sk_SSL_CIPHER_num(dup)); + + /* error case because connection has not been established yet */ + AssertIntEQ(sk_SSL_CIPHER_find(sk, SSL_get_current_cipher(ssl)), -1); + sk_SSL_CIPHER_free(dup); + + /* sk is pointer to internal struct that should be free'd in SSL_free */ + SSL_free(ssl); + SSL_CTX_free(ctx); + + printf(resultFmt, passed); + #endif /* defined(OPENSSL_EXTRA) && !defined(NO_CERTS) && \ + !defined(NO_FILESYSTEM) && !defined(NO_RSA) */ +} + /* Testing wolfSSL_set_tlsext_status_type funciton. * PRE: OPENSSL and HAVE_CERTIFICATE_STATUS_REQUEST defined. */ @@ -20866,6 +21155,20 @@ static void test_wolfSSL_PEM_read_bio(void) } +#if defined(OPENSSL_EXTRA) +static long bioCallback(BIO *bio, int cmd, const char* argp, int argi, + long argl, long ret) +{ + (void)bio; + (void)cmd; + (void)argp; + (void)argi; + (void)argl; + return ret; +} +#endif + + static void test_wolfSSL_BIO(void) { #if defined(OPENSSL_EXTRA) @@ -20891,6 +21194,7 @@ static void test_wolfSSL_BIO(void) AssertIntEQ(BIO_read(bio1, buff, 2), WOLFSSL_BIO_UNSET); AssertIntEQ(BIO_write(bio1, buff, 2), WOLFSSL_BIO_UNSET); + AssertIntEQ(BIO_set_nbio(bio1, 1), 1); AssertIntEQ(BIO_set_write_buf_size(bio1, 20), WOLFSSL_SUCCESS); AssertIntEQ(BIO_set_write_buf_size(bio2, 8), WOLFSSL_SUCCESS); AssertIntEQ(BIO_make_bio_pair(bio1, bio2), WOLFSSL_SUCCESS); @@ -21053,6 +21357,29 @@ static void test_wolfSSL_BIO(void) } #endif /* !defined(NO_FILESYSTEM) */ + /* BIO info callback */ + { + const char* testArg = "test"; + BIO* cb_bio; + AssertNotNull(cb_bio = BIO_new(BIO_s_mem())); + + BIO_set_callback(cb_bio, bioCallback); + AssertNotNull(BIO_get_callback(cb_bio)); + BIO_set_callback(cb_bio, NULL); + AssertNull(BIO_get_callback(cb_bio)); + + BIO_set_callback_arg(cb_bio, (char*)testArg); + AssertStrEQ(BIO_get_callback_arg(cb_bio), testArg); + AssertNull(BIO_get_callback_arg(NULL)); + + BIO_free(cb_bio); + } + + /* BIO_vfree */ + AssertNotNull(bio1 = BIO_new(BIO_s_bio())); + BIO_vfree(NULL); + BIO_vfree(bio1); + printf(resultFmt, passed); #endif } @@ -21277,10 +21604,146 @@ static void test_wolfSSL_X509(void) X509_free(x509); XFCLOSE(fp); + /* X509_up_ref test */ + AssertIntEQ(X509_up_ref(NULL), 0); + AssertNotNull(x509 = X509_new()); /* refCount = 1 */ + AssertIntEQ(X509_up_ref(x509), 1); /* refCount = 2 */ + AssertIntEQ(X509_up_ref(x509), 1); /* refCount = 3 */ + X509_free(x509); /* refCount = 2 */ + X509_free(x509); /* refCount = 1 */ + X509_free(x509); /* refCount = 0, free */ + printf(resultFmt, passed); #endif } +static void test_wolfSSL_X509_get_ext_count(void) +{ +#if defined(OPENSSL_ALL) && !defined(NO_CERTS) && !defined(NO_FILESYSTEM) + WOLFSSL_X509* x509; + const char ocspRootCaFile[] = "./certs/ocsp/root-ca-cert.pem"; + + printf(testingFmt, "wolfSSL_X509_get_ext_count()"); + + /* NULL parameter check */ + AssertIntEQ(X509_get_ext_count(NULL), WOLFSSL_FAILURE); + + AssertNotNull(x509 = wolfSSL_X509_load_certificate_file(svrCertFile, + SSL_FILETYPE_PEM)); + AssertIntEQ(X509_get_ext_count(x509), 3); + wolfSSL_X509_free(x509); + + AssertNotNull(x509 = wolfSSL_X509_load_certificate_file(ocspRootCaFile, + SSL_FILETYPE_PEM)); + AssertIntEQ(X509_get_ext_count(x509), 5); + wolfSSL_X509_free(x509); + + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_X509_sign(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) && \ + !defined(NO_CERTS) && defined(WOLFSSL_CERT_GEN) && defined(WOLFSSL_CERT_REQ) + X509_NAME *name; + X509 *x509; + EVP_PKEY *pub; + EVP_PKEY *priv; +#if defined(USE_CERT_BUFFERS_1024) + const unsigned char* rsaPriv = (const unsigned char*)client_key_der_1024; + unsigned char* rsaPub = (unsigned char*)client_keypub_der_1024; + long clientKeySz = (long)sizeof_client_key_der_1024; + long clientPubKeySz = (long)sizeof_client_keypub_der_1024; +#elif defined(USE_CERT_BUFFERS_2048) + const unsigned char* rsaPriv = (const unsigned char*)client_key_der_2048; + unsigned char* rsaPub = (unsigned char*)client_keypub_der_2048; + long clientKeySz = (long)sizeof_client_key_der_2048; + long clientPubKeySz = (long)sizeof_client_keypub_der_2048; +#endif + + printf(testingFmt, "wolfSSL_X509_sign"); + + /* Set X509_NAME fields */ + AssertNotNull(name = X509_NAME_new()); + AssertIntEQ(X509_NAME_add_entry_by_txt(name, "country", MBSTRING_UTF8, + (byte*)"US", 2, -1, 0), WOLFSSL_SUCCESS); + AssertIntEQ(X509_NAME_add_entry_by_txt(name, "commonName", MBSTRING_UTF8, + (byte*)"wolfssl.com", 11, -1, 0), WOLFSSL_SUCCESS); + AssertIntEQ(X509_NAME_add_entry_by_txt(name, "emailAddress", MBSTRING_UTF8, + (byte*)"support@wolfssl.com", 19, -1, 0), WOLFSSL_SUCCESS); + + /* Get private and public keys */ + AssertNotNull(priv = wolfSSL_d2i_PrivateKey(EVP_PKEY_RSA, NULL, &rsaPriv, + clientKeySz)); + AssertNotNull(pub = wolfSSL_d2i_PUBKEY(NULL, &rsaPub, clientPubKeySz)); + AssertNotNull(x509 = X509_new()); + + /* Set subject name, add pubkey, and sign certificate */ + AssertIntEQ(X509_set_subject_name(x509, name), WOLFSSL_SUCCESS); + AssertIntEQ(X509_set_pubkey(x509, pub), WOLFSSL_SUCCESS); + /* Test invalid parameters */ + AssertIntEQ(X509_sign(NULL, priv, EVP_sha256()), 0); + AssertIntEQ(X509_sign(x509, NULL, EVP_sha256()), 0); + AssertIntEQ(X509_sign(x509, priv, NULL), 0); + /* Valid case - size should be 798 */ + AssertIntEQ(X509_sign(x509, priv, EVP_sha256()), 798); + + X509_NAME_free(name); + EVP_PKEY_free(priv); + EVP_PKEY_free(pub); + X509_free(x509); + + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_X509_get0_tbs_sigalg(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) + X509* x509 = NULL; + const X509_ALGOR* alg; + printf(testingFmt, "wolfSSL_X509_get0_tbs_sigalg"); + + AssertNotNull(x509 = X509_new()); + + AssertNull(alg = X509_get0_tbs_sigalg(NULL)); + AssertNotNull(alg = X509_get0_tbs_sigalg(x509)); + + X509_free(x509); + + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_X509_ALGOR_get0(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) && !defined(NO_SHA256) + X509* x509 = NULL; + ASN1_OBJECT* obj = NULL; + const X509_ALGOR* alg; + printf(testingFmt, "wolfSSL_X509_ALGOR_get0"); + + AssertNotNull(x509 = wolfSSL_X509_load_certificate_file(cliCertFile, + SSL_FILETYPE_PEM)); + AssertNotNull(alg = X509_get0_tbs_sigalg(x509)); + + /* Invalid case */ + X509_ALGOR_get0(&obj, NULL, NULL, NULL); + AssertNull(obj); + + /* Valid case */ + X509_ALGOR_get0(&obj, NULL, NULL, alg); + AssertNotNull(obj); + /* Make sure NID of X509_ALGOR is Sha256 with RSA */ + AssertIntEQ(OBJ_obj2nid(obj), CTC_SHA256wRSA); + + X509_free(x509); + + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_X509_VERIFY_PARAM(void) { @@ -21324,6 +21787,47 @@ static void test_wolfSSL_X509_VERIFY_PARAM(void) #endif } +static void test_wolfSSL_X509_get_X509_PUBKEY(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) + X509* x509 = NULL; + X509_PUBKEY* pubKey; + printf(testingFmt, "wolfSSL_X509_get_X509_PUBKEY"); + + AssertNotNull(x509 = X509_new()); + + AssertNull(pubKey = wolfSSL_X509_get_X509_PUBKEY(NULL)); + AssertNotNull(pubKey = wolfSSL_X509_get_X509_PUBKEY(x509)); + + X509_free(x509); + + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_X509_PUBKEY_get0_param(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) && !defined(NO_SHA256) + X509* x509 = NULL; + ASN1_OBJECT* obj = NULL; + X509_PUBKEY* pubKey; + printf(testingFmt, "wolfSSL_X509_get_X509_PUBKEY"); + + AssertNotNull(x509 = wolfSSL_X509_load_certificate_file(cliCertFile, + SSL_FILETYPE_PEM)); + + AssertNotNull(pubKey = wolfSSL_X509_get_X509_PUBKEY(x509)); + X509_PUBKEY_get0_param(&obj, NULL, 0, NULL, pubKey); + AssertNotNull(pubKey); + + AssertIntEQ(OBJ_obj2nid(obj), RSAk); + + X509_free(x509); +// AssertIntEQ(1,0); + + printf(resultFmt, passed); +#endif +} static void test_wolfSSL_RAND(void) { @@ -21630,6 +22134,12 @@ static void test_wolfSSL_ERR_put_error(void) AssertNull(file); AssertIntEQ(ERR_get_error_line_data(&file, &line, NULL, NULL), 0); + PEMerr(4,4); + #if (defined(OPENSSL_EXTRA) && !defined(OPENSSL_ALL)) || defined(DEBUG_WOLFSSL_VERBOSE) + AssertIntEQ(ERR_get_error(), 4); + #else + AssertIntEQ(ERR_get_error(), -4); + #endif /* Empty and free up all error nodes */ ERR_clear_error(); @@ -21643,6 +22153,36 @@ static void test_wolfSSL_ERR_put_error(void) } +static void test_wolfSSL_ERR_print_errors(void) +{ + #if defined(OPENSSL_EXTRA) && defined(DEBUG_WOLFSSL) + BIO* bio; + char buf[1024]; + + printf(testingFmt, "wolfSSL_ERR_print_errors()"); + + + AssertNotNull(bio = BIO_new(BIO_s_mem())); + ERR_clear_error(); /* clear out any error nodes */ + ERR_put_error(0,SYS_F_ACCEPT, -173, "ssl.c", 0); + ERR_put_error(0,SYS_F_BIND, -273, "asn.c", 100); + + ERR_print_errors(bio); + AssertIntEQ(BIO_gets(bio, buf, sizeof(buf)), 56); + AssertIntEQ(XSTRNCMP("error:173:wolfSSL library:Bad function argument:ssl.c:0", + buf, 55), 0); + AssertIntEQ(BIO_gets(bio, buf, sizeof(buf)), 57); + AssertIntEQ(XSTRNCMP("error:273:wolfSSL library:unknown error number:asn.c:100", + buf, 56), 0); + AssertIntEQ(BIO_gets(bio, buf, sizeof(buf)), 0); + AssertIntEQ(ERR_get_error_line(NULL, NULL), 0); + + BIO_free(bio); + printf(resultFmt, passed); + #endif +} + + static void test_wolfSSL_HMAC(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_SHA256) @@ -21815,6 +22355,124 @@ static void test_wolfSSL_i2a_ASN1_OBJECT(void) #endif } +static void test_wolfSSL_OBJ_cmp(void) +{ +#if defined(OPENSSL_EXTRA) && !defined(NO_SHA256) + ASN1_OBJECT *obj = NULL; + ASN1_OBJECT *obj2 = NULL; + + printf(testingFmt, "wolfSSL_OBJ_cmp()"); + + AssertNotNull(obj = OBJ_nid2obj(NID_any_policy)); + AssertNotNull(obj2 = OBJ_nid2obj(NID_sha256)); + + AssertIntEQ(OBJ_cmp(NULL, NULL), WOLFSSL_FATAL_ERROR); + AssertIntEQ(OBJ_cmp(obj, NULL), WOLFSSL_FATAL_ERROR); + AssertIntEQ(OBJ_cmp(NULL, obj2), WOLFSSL_FATAL_ERROR); + AssertIntEQ(OBJ_cmp(obj, obj2), WOLFSSL_FATAL_ERROR); + AssertIntEQ(OBJ_cmp(obj, obj), 0); + AssertIntEQ(OBJ_cmp(obj2, obj2), 0); + + ASN1_OBJECT_free(obj); + ASN1_OBJECT_free(obj2); + + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_OBJ_txt2nid(void) +{ +#if !defined(NO_WOLFSSL_STUB) && defined(WOLFSSL_APACHE_HTTPD) + int i; + static const struct { + const char* sn; + const char* ln; + const char* oid; + int nid; + } testVals[] = { + { "tlsfeature", "TLS Feature", "1.3.6.1.5.5.7.1.24", NID_tlsfeature }, + { "id-on-dnsSRV", "SRVName otherName form", "1.3.6.1.5.5.7.8.7", + NID_id_on_dnsSRV }, + { "msUPN", "Microsoft Universal Principal Name", + "1.3.6.1.4.1.311.20.2.3", NID_ms_upn }, + { NULL, NULL, NULL, NID_undef } + }; + + printf(testingFmt, "wolfSSL_OBJ_txt2nid()"); + + /* Invalid cases */ + AssertIntEQ(OBJ_txt2nid(NULL), NID_undef); + AssertIntEQ(OBJ_txt2nid("Bad name"), NID_undef); + + /* Valid cases */ + for (i = 0; testVals[i].sn != NULL; i++) { + AssertIntEQ(OBJ_txt2nid(testVals[i].sn), testVals[i].nid); + AssertIntEQ(OBJ_txt2nid(testVals[i].ln), testVals[i].nid); + AssertIntEQ(OBJ_txt2nid(testVals[i].oid), testVals[i].nid); + } + + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_OBJ_txt2obj(void) +{ +#if defined(WOLFSSL_APACHE_HTTPD) || (defined(OPENSSL_EXTRA) && \ + defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_CERT_GEN)) + int i; + char buf[50]; + ASN1_OBJECT* obj; + static const struct { + const char* oidStr; + const char* sn; + const char* ln; + } objs_list[] = { + #if defined(WOLFSSL_APACHE_HTTPD) + { "1.3.6.1.5.5.7.1.24", "tlsfeature", "TLS Feature" }, + { "1.3.6.1.5.5.7.8.7", "id-on-dnsSRV", "SRVName otherName form" }, + #endif + { "2.5.29.19", "X509 basic ca", "X509v3 Basic Constraints"}, + { NULL, NULL, NULL } + }; + + printf(testingFmt, "wolfSSL_OBJ_txt2obj()"); + + AssertNull(obj = OBJ_txt2obj("Bad name", 0)); + AssertNull(obj = OBJ_txt2obj(NULL, 0)); + + for (i = 0; objs_list[i].oidStr != NULL; i++) { + /* Test numerical value of oid (oidStr) */ + AssertNotNull(obj = OBJ_txt2obj(objs_list[i].oidStr, 1)); + /* Convert object back to text to confirm oid is correct */ + wolfSSL_OBJ_obj2txt(buf, (int)sizeof(buf), obj, 1); + AssertIntEQ(XSTRNCMP(buf, objs_list[i].oidStr, (int)XSTRLEN(buf)), 0); + ASN1_OBJECT_free(obj); + XMEMSET(buf, 0, sizeof(buf)); + + /* Test short name (sn) */ + AssertNull(obj = OBJ_txt2obj(objs_list[i].sn, 1)); + AssertNotNull(obj = OBJ_txt2obj(objs_list[i].sn, 0)); + /* Convert object back to text to confirm oid is correct */ + wolfSSL_OBJ_obj2txt(buf, (int)sizeof(buf), obj, 1); + AssertIntEQ(XSTRNCMP(buf, objs_list[i].oidStr, (int)XSTRLEN(buf)), 0); + ASN1_OBJECT_free(obj); + XMEMSET(buf, 0, sizeof(buf)); + + /* Test long name (ln) - should fail when no_name = 1 */ + AssertNull(obj = OBJ_txt2obj(objs_list[i].ln, 1)); + AssertNotNull(obj = OBJ_txt2obj(objs_list[i].ln, 0)); + /* Convert object back to text to confirm oid is correct */ + wolfSSL_OBJ_obj2txt(buf, (int)sizeof(buf), obj, 1); + AssertIntEQ(XSTRNCMP(buf, objs_list[i].oidStr, (int)XSTRLEN(buf)), 0); + ASN1_OBJECT_free(obj); + XMEMSET(buf, 0, sizeof(buf)); + } + + printf(resultFmt, passed); + +#endif +} + static void test_wolfSSL_X509_NAME_ENTRY(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_CERTS) \ @@ -21866,6 +22524,169 @@ static void test_wolfSSL_X509_NAME_ENTRY(void) } +static void test_wolfSSL_X509_set_name(void) +{ +#if defined(OPENSSL_ALL) && !defined(NO_CERTS) + X509* x509; + X509_NAME* name; + + printf(testingFmt, "wolfSSL_X509_set_name()"); + + AssertNotNull(name = X509_NAME_new()); + AssertIntEQ(X509_NAME_add_entry_by_txt(name, "commonName", MBSTRING_UTF8, + (byte*)"wolfssl.com", 11, 0, 1), + WOLFSSL_SUCCESS); + AssertIntEQ(X509_NAME_add_entry_by_txt(name, "emailAddress", MBSTRING_UTF8, + (byte*)"support@wolfssl.com", 19, -1, + 1), WOLFSSL_SUCCESS); + AssertNotNull(x509 = X509_new()); + + AssertIntEQ(X509_set_subject_name(NULL, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_set_subject_name(x509, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_set_subject_name(NULL, name), WOLFSSL_FAILURE); + AssertIntEQ(X509_set_subject_name(x509, name), WOLFSSL_SUCCESS); + + AssertIntEQ(X509_set_issuer_name(NULL, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_set_issuer_name(x509, NULL), WOLFSSL_FAILURE); + AssertIntEQ(X509_set_issuer_name(NULL, name), WOLFSSL_FAILURE); + AssertIntEQ(X509_set_issuer_name(x509, name), WOLFSSL_SUCCESS); + + X509_free(x509); + X509_NAME_free(name); + + printf(resultFmt, passed); +#endif /* OPENSSL_ALL && !NO_CERTS */ +} + +static void test_wolfSSL_X509_set_notAfter(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) \ + && !defined(NO_ASN1_TIME) && !defined(USER_TIME) && \ + !defined(TIME_OVERRIDES) && !defined(NO_CERTS) && \ + defined(WOLFSSL_CERT_GEN) && defined(WOLFSSL_CERT_REQ) + + X509* x; + BIO* bio; + ASN1_TIME *asn_time, *time_check; + const int year = 365*24*60*60; + const int day = 24*60*60; + const int hour = 60*60; + const int mini = 60; + int offset_day; + unsigned char buf[25]; + time_t t; + + printf(testingFmt, "wolfSSL_X509_set_notAfter()"); + /* + * Setup asn_time. APACHE HTTPD uses time(NULL) + */ + t = (time_t)107 * year + 31 * day + 34 * hour + 30 * mini + 7 * day; + offset_day = 7; + /* + * Free these. + */ + asn_time = wolfSSL_ASN1_TIME_adj(NULL, t, offset_day, 0); + AssertNotNull(asn_time); + AssertNotNull(x = X509_new()); + AssertNotNull(bio = BIO_new(BIO_s_mem())); + /* + * Tests + */ + AssertTrue(wolfSSL_X509_set_notAfter(x, asn_time)); + /* time_check is simply (ANS1_TIME*)x->notAfter */ + AssertNotNull(time_check = X509_get_notAfter(x)); + /* ANS1_TIME_check validates by checking if arguement can be parsed */ + AssertIntEQ(ASN1_TIME_check(time_check), WOLFSSL_SUCCESS); + /* Convert to human readable format and compare to intended date */ + AssertIntEQ(ASN1_TIME_print(bio,time_check), 1); + AssertIntEQ(BIO_read(bio, buf, sizeof(buf)), 24); + AssertIntEQ(XMEMCMP(buf, "Jan 20 10:30:00 2077 GMT", sizeof(buf) - 1), 0); + /* + * Cleanup + */ + XFREE(asn_time,NULL,DYNAMIC_TYPE_OPENSSL); + X509_free(x); + BIO_free(bio); + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_X509_set_notBefore(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) \ + && !defined(NO_ASN1_TIME) && !defined(USER_TIME) && \ + !defined(TIME_OVERRIDES) && !defined(NO_CERTS) && \ + defined(WOLFSSL_CERT_GEN) && defined(WOLFSSL_CERT_REQ) + + X509* x; + BIO* bio; + ASN1_TIME *asn_time, *time_check; + const int year = 365*24*60*60; + const int day = 24*60*60; + const int hour = 60*60; + const int mini = 60; + int offset_day; + unsigned char buf[25]; + time_t t; + + printf(testingFmt, "wolfSSL_X509_set_notBefore()"); + /* + * Setup asn_time. APACHE HTTPD uses time(NULL) + */ + t = (time_t)49 * year + 125 * day + 20 * hour + 30 * mini + 7 * day; + offset_day = 7; + + /* + * Free these. + */ + asn_time = wolfSSL_ASN1_TIME_adj(NULL, t, offset_day, 0); + AssertNotNull(asn_time); + AssertNotNull(x = X509_new()); + AssertNotNull(bio = BIO_new(BIO_s_mem())); + AssertIntEQ(ASN1_TIME_check(asn_time), WOLFSSL_SUCCESS); + + /* + * Main Tests + */ + AssertTrue(wolfSSL_X509_set_notBefore(x, asn_time)); + /* time_check == (ANS1_TIME*)x->notBefore */ + AssertNotNull(time_check = X509_get_notBefore(x)); + /* ANS1_TIME_check validates by checking if arguement can be parsed */ + AssertIntEQ(ASN1_TIME_check(time_check), WOLFSSL_SUCCESS); + /* Convert to human readable format and compare to intended date */ + AssertIntEQ(ASN1_TIME_print(bio,time_check), 1); + AssertIntEQ(BIO_read(bio, buf, sizeof(buf)), 24); + AssertIntEQ(XMEMCMP(buf, "May 8 20:30:00 2019 GMT", sizeof(buf) - 1), 0); + /* + * Cleanup + */ + XFREE(asn_time,NULL,DYNAMIC_TYPE_OPENSSL); + X509_free(x); + BIO_free(bio); + printf(resultFmt, passed); +#endif +} + +static void test_wolfSSL_X509_set_version(void) +{ +#if (defined(OPENSSL_ALL) || defined(WOLFSSL_APACHE_HTTPD)) && \ + !defined(NO_CERTS) && defined(WOLFSSL_CERT_GEN) && defined(WOLFSSL_CERT_REQ) + X509* x509; + long v = 2L; + + AssertNotNull(x509 = X509_new()); + /* These should pass. */ + AssertTrue(wolfSSL_X509_set_version(x509, v)); + AssertIntEQ(v, wolfSSL_X509_get_version(x509)); + /* Fail Case: When v(long) is greater than x509->version(int). */ + v = (long) INT_MAX+1; + AssertFalse(wolfSSL_X509_set_version(x509, v)); + /* Cleanup */ + X509_free(x509); + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_BIO_gets(void) { #if defined(OPENSSL_EXTRA) @@ -21876,7 +22697,7 @@ static void test_wolfSSL_BIO_gets(void) char bio_buffer[20]; int bufferSz = 20; - printf(testingFmt, "wolfSSL_X509_BIO_gets()"); + printf(testingFmt, "wolfSSL_BIO_gets()"); /* try with bad args */ AssertNull(bio = BIO_new_mem_buf(NULL, sizeof(msg))); @@ -21991,6 +22812,34 @@ static void test_wolfSSL_BIO_gets(void) } +static void test_wolfSSL_BIO_puts(void) +{ + #if defined(OPENSSL_EXTRA) + BIO* bio; + char input[] = "hello\0world\n.....ok\n\0"; + char output[128]; + + printf(testingFmt, "wolfSSL_BIO_puts()"); + + XMEMSET(output, 0, sizeof(output)); + AssertNotNull(bio = BIO_new(BIO_s_mem())); + AssertIntEQ(BIO_puts(bio, input), 5); + AssertIntEQ(BIO_pending(bio), 5); + AssertIntEQ(BIO_puts(bio, input + 6), 14); + AssertIntEQ(BIO_pending(bio), 19); + AssertIntEQ(BIO_gets(bio, output, sizeof(output)), 11); + AssertStrEQ(output, "helloworld\n"); + AssertIntEQ(BIO_pending(bio), 8); + AssertIntEQ(BIO_gets(bio, output, sizeof(output)), 8); + AssertStrEQ(output, ".....ok\n"); + AssertIntEQ(BIO_pending(bio), 0); + AssertIntEQ(BIO_puts(bio, ""), -1); + + BIO_free(bio); + printf(resultFmt, passed); + #endif +} + static void test_wolfSSL_BIO_write(void) { #if defined(OPENSSL_EXTRA) && defined(WOLFSSL_BASE64_ENCODE) @@ -22046,12 +22895,37 @@ static void test_wolfSSL_BIO_write(void) XMEMSET(out, 0, sz); AssertIntEQ((sz = BIO_read(bio, out, sz)), 16); AssertIntEQ(XMEMCMP(out, msg, sz), 0); + BIO_set_retry_read(bio); BIO_free_all(bio); /* frees bio64s also */ printf(resultFmt, passed); #endif } + +static void test_wolfSSL_BIO_printf(void) +{ + #if defined(OPENSSL_ALL) + BIO* bio; + int sz = 7; + char msg[] = "TLS 1.3 for the world"; + char out[60]; + char expected[] = "TLS 1.3 for the world : sz = 7"; + + printf(testingFmt, "wolfSSL_BIO_printf()"); + + XMEMSET(out, 0, sizeof(out)); + AssertNotNull(bio = BIO_new(BIO_s_mem())); + AssertIntEQ(BIO_printf(bio, "%s : sz = %d", msg, sz), 30); + AssertIntEQ(BIO_printf(NULL, ""), WOLFSSL_FATAL_ERROR); + AssertIntEQ(BIO_read(bio, out, sizeof(out)), 30); + AssertIntEQ(XSTRNCMP(out, expected, sizeof(expected)), 0); + BIO_free(bio); + + printf(resultFmt, passed); + #endif +} + static void test_wolfSSL_SESSION(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_FILESYSTEM) && !defined(NO_CERTS) && \ @@ -22521,6 +23395,57 @@ static void test_wolfSSL_RSA_DER(void) #endif } +static void test_wolfSSL_RSA_get0_key(void) +{ +#if defined(OPENSSL_EXTRA) && !defined(NO_RSA) && !defined(HAVE_USER_RSA) + RSA *rsa = NULL; + const BIGNUM* n = NULL; + const BIGNUM* e = NULL; + const BIGNUM* d = NULL; + + const unsigned char* der = NULL; + int derSz = 0; + +#ifdef USE_CERT_BUFFERS_1024 + der = client_key_der_1024; + derSz = sizeof_client_key_der_1024; +#elif defined(USE_CERT_BUFFERS_2048) + der = client_key_der_2048; + derSz = sizeof_client_key_der_2048; +#endif + + printf(testingFmt, "test_wolfSSL_RSA_get0_key()"); + + if (der != NULL) { + RSA_get0_key(NULL, NULL, NULL, NULL); + RSA_get0_key(rsa, NULL, NULL, NULL); + RSA_get0_key(NULL, &n, &e, &d); + AssertNull(n); + AssertNull(e); + AssertNull(d); + + AssertNotNull(d2i_RSAPrivateKey(&rsa, &der, derSz)); + AssertNotNull(rsa); + + RSA_get0_key(rsa, NULL, NULL, NULL); + RSA_get0_key(rsa, &n, NULL, NULL); + AssertNotNull(n); + RSA_get0_key(rsa, NULL, &e, NULL); + AssertNotNull(e); + RSA_get0_key(rsa, NULL, NULL, &d); + AssertNotNull(d); + RSA_get0_key(rsa, &n, &e, &d); + AssertNotNull(n); + AssertNotNull(e); + AssertNotNull(d); + + RSA_free(rsa); + } + + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_verify_depth(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_RSA) @@ -23876,29 +24801,6 @@ static void test_wolfSSL_X509_get_ext_by_NID(void) #endif } -static void test_wolfSSL_X509_get_ext_count(void) -{ -#if !defined(NO_FILESYSTEM) && defined (OPENSSL_ALL) - FILE* f; - WOLFSSL_X509* x509; - int ret = 0; - - AssertNotNull(f = fopen("./certs/server-cert.pem", "rb")); - AssertNotNull(x509 = wolfSSL_PEM_read_X509(f, NULL, NULL, NULL)); - fclose(f); - - printf(testingFmt, "wolfSSL_X509_get_ext_count() valid input"); - AssertIntEQ((ret = wolfSSL_X509_get_ext_count(x509)), 3); - printf(resultFmt, ret == 3 ? passed : failed); - - printf(testingFmt, "wolfSSL_X509_get_ext_count() NULL argument"); - AssertIntEQ((ret = wolfSSL_X509_get_ext_count(NULL)), WOLFSSL_FAILURE); - printf(resultFmt, ret == WOLFSSL_FAILURE ? passed : failed); - - wolfSSL_X509_free(x509); -#endif -} - static void test_wolfSSL_X509_EXTENSION_new(void) { #if defined (OPENSSL_ALL) @@ -24058,6 +24960,119 @@ static void test_wolfSSL_X509_cmp(void) #endif } +static void test_wolfSSL_PKEY_up_ref() +{ +#if defined(OPENSSL_ALL) + EVP_PKEY* pkey; + printf(testingFmt, "wolfSSL_PKEY_up_ref()"); + + pkey = EVP_PKEY_new(); + AssertIntEQ(EVP_PKEY_up_ref(NULL), 0); + AssertIntEQ(EVP_PKEY_up_ref(pkey), 1); + EVP_PKEY_free(pkey); + AssertIntEQ(EVP_PKEY_up_ref(pkey), 1); + EVP_PKEY_free(pkey); + EVP_PKEY_free(pkey); + + printf(resultFmt, "passed"); +#endif +} + +static void test_wolfSSL_i2d_PrivateKey() +{ +#if (!defined(NO_RSA) || defined(HAVE_ECC)) && defined(OPENSSL_EXTRA) + + printf(testingFmt, "wolfSSL_i2d_PrivateKey()"); +#if !defined(NO_RSA) && defined(USE_CERT_BUFFERS_2048) + { + EVP_PKEY* pkey; + const unsigned char* server_key = (const unsigned char*)server_key_der_2048; + unsigned char buf[FOURK_BUF]; + unsigned char* pt; + int bufSz; + + AssertNotNull(pkey = d2i_PrivateKey(EVP_PKEY_RSA, NULL, &server_key, + (long)sizeof_server_key_der_2048)); + AssertIntEQ(i2d_PrivateKey(pkey, NULL), 1193); + pt = buf; + AssertIntEQ((bufSz = i2d_PrivateKey(pkey, &pt)), 1193); + AssertIntNE((pt - buf), 0); + AssertIntEQ(XMEMCMP(buf, server_key_der_2048, bufSz), 0); + EVP_PKEY_free(pkey); + } +#endif +#if defined(OPENSSL_EXTRA) && defined(HAVE_ECC) && defined(USE_CERT_BUFFERS_256) + { + EVP_PKEY* pkey; + const unsigned char* client_key = + (const unsigned char*)ecc_clikey_der_256; + unsigned char buf[FOURK_BUF]; + unsigned char* pt; + int bufSz; + + AssertNotNull((pkey = d2i_PrivateKey(EVP_PKEY_EC, NULL, &client_key, + sizeof_ecc_clikey_der_256))); + AssertIntEQ(i2d_PrivateKey(pkey, NULL), 121); + pt = buf; + AssertIntEQ((bufSz = i2d_PrivateKey(pkey, &pt)), 121); + AssertIntNE((pt - buf), 0); + AssertIntEQ(XMEMCMP(buf, ecc_clikey_der_256, bufSz), 0); + EVP_PKEY_free(pkey); + } +#endif + + printf(resultFmt, "passed"); +#endif +} + +static void test_wolfSSL_OCSP_get0_info() +{ +#if defined(OPENSSL_ALL) && defined(HAVE_OCSP) && !defined(NO_FILESYSTEM) + X509* cert; + X509* issuer; + OCSP_CERTID* id; + + ASN1_STRING* name = NULL; + ASN1_OBJECT* pmd = NULL; + ASN1_STRING* keyHash = NULL; + ASN1_INTEGER* serial = NULL; + ASN1_INTEGER* x509Int = NULL; + + printf(testingFmt, "wolfSSL_OCSP_get0_info()"); + + AssertNotNull(cert = + wolfSSL_X509_load_certificate_file(svrCertFile, SSL_FILETYPE_PEM)); + AssertNotNull(issuer = + wolfSSL_X509_load_certificate_file(caCertFile, SSL_FILETYPE_PEM)); + + id = OCSP_cert_to_id(NULL, cert, issuer); + AssertNotNull(id); + + AssertIntEQ(OCSP_id_get0_info(NULL, NULL, NULL, NULL, NULL), 0); + AssertIntEQ(OCSP_id_get0_info(NULL, NULL, NULL, NULL, id), 1); + + /* name, pmd, keyHash not supported yet, expect failure if not NULL */ + AssertIntEQ(OCSP_id_get0_info(&name, NULL, NULL, NULL, id), 0); + AssertIntEQ(OCSP_id_get0_info(NULL, &pmd, NULL, NULL, id), 0); + AssertIntEQ(OCSP_id_get0_info(NULL, NULL, &keyHash, NULL, id), 0); + + AssertIntEQ(OCSP_id_get0_info(NULL, NULL, NULL, &serial, id), 1); + AssertNotNull(serial); + + /* compare serial number to one in cert, should be equal */ + x509Int = X509_get_serialNumber(cert); + AssertNotNull(x509Int); + AssertIntEQ(x509Int->dataMax, serial->dataMax); + AssertIntEQ(XMEMCMP(x509Int->data, serial->data, serial->dataMax), 0); + + ASN1_INTEGER_free(x509Int); + OCSP_CERTID_free(id); + X509_free(cert); + X509_free(issuer); + + printf(resultFmt, "passed"); +#endif /* OPENSSL_EXTRA & HAVE_OCSP */ +} static void test_no_op_functions(void) { @@ -24068,7 +25083,7 @@ static void test_no_op_functions(void) SSL_load_error_strings(); ENGINE_load_builtin_engines(); OpenSSL_add_all_ciphers(); - CRYPTO_malloc_init(); + AssertIntEQ(CRYPTO_malloc_init(), 0); printf(resultFmt, passed); #endif @@ -24733,6 +25748,10 @@ static void test_sk_X509(void) AssertIntEQ(sk_X509_num(s), 0); sk_X509_free(s); + AssertNotNull(s = sk_X509_new_null()); + AssertIntEQ(sk_X509_num(s), 0); + sk_X509_free(s); + AssertNotNull(s = sk_X509_new()); sk_X509_push(s, (X509*)1); AssertIntEQ(sk_X509_num(s), 1); @@ -25981,7 +27000,6 @@ static void test_wolfSSL_PEM_read(void) #endif } - static void test_wolfssl_EVP_aes_gcm(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_AES) && defined(HAVE_AESGCM) @@ -26062,6 +27080,49 @@ static void test_wolfssl_EVP_aes_gcm(void) #endif /* OPENSSL_EXTRA && !NO_AES && HAVE_AESGCM */ } +static void test_wolfSSL_PEM_X509_INFO_read_bio(void) +{ +#if defined(OPENSSL_ALL) && !defined(NO_FILESYSTEM) + BIO* bio; + X509_INFO* info; + STACK_OF(X509_INFO)* sk; + char* subject; + char exp1[] = "/C=US/ST=Montana/L=Bozeman/O=Sawtooth/OU=Consulting/CN=www.wolfssl.com/emailAddress=info@wolfssl.com"; + char exp2[] = "/C=US/ST=Montana/L=Bozeman/O=wolfSSL/OU=Support/CN=www.wolfssl.com/emailAddress=info@wolfssl.com"; + + printf(testingFmt, "wolfSSL_PEM_X509_INFO_read_bio"); + AssertNotNull(bio = BIO_new(BIO_s_file())); + AssertIntGT(BIO_read_filename(bio, svrCertFile), 0); + AssertNotNull(sk = PEM_X509_INFO_read_bio(bio, NULL, NULL, NULL)); + AssertIntEQ(sk_X509_INFO_num(sk), 2); + + /* using dereference to maintain testing for Apache port*/ + AssertNotNull(info = sk_X509_INFO_pop(sk)); + AssertNotNull(info->x_pkey); + AssertNotNull(info->x_pkey->dec_pkey); + AssertIntEQ(EVP_PKEY_bits(info->x_pkey->dec_pkey), 2048); + AssertNotNull(subject = + X509_NAME_oneline(X509_get_subject_name(info->x509), 0, 0)); + + AssertIntEQ(0, XSTRNCMP(subject, exp1, sizeof(exp1))); + XFREE(subject, 0, DYNAMIC_TYPE_OPENSSL); + X509_INFO_free(info); + + AssertNotNull(info = sk_X509_INFO_pop(sk)); + AssertNotNull(subject = + X509_NAME_oneline(X509_get_subject_name(info->x509), 0, 0)); + + AssertIntEQ(0, XSTRNCMP(subject, exp2, sizeof(exp2))); + XFREE(subject, 0, DYNAMIC_TYPE_OPENSSL); + X509_INFO_free(info); + AssertNull(info = sk_X509_INFO_pop(sk)); + + sk_X509_INFO_pop_free(sk, X509_INFO_free); + BIO_free(bio); + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_X509_NAME_ENTRY_get_object() { #if defined(OPENSSL_EXTRA) && !defined(NO_FILESYSTEM) && !defined(NO_RSA) @@ -26636,6 +27697,7 @@ void ApiTest(void) test_wolfSSL_DES(); test_wolfSSL_certs(); test_wolfSSL_ASN1_TIME_print(); + test_wolfSSL_ASN1_UTCTIME_print(); test_wolfSSL_ASN1_GENERALIZEDTIME_free(); test_wolfSSL_private_keys(); test_wolfSSL_PEM_PrivateKey(); @@ -26654,7 +27716,9 @@ void ApiTest(void) test_wolfSSL_ERR_peek_last_error_line(); #endif test_wolfSSL_set_options(); + test_wolfSSL_sk_SSL_CIPHER(); test_wolfSSL_X509_STORE_CTX(); + test_wolfSSL_X509_STORE_CTX_get0_current_issuer(); test_wolfSSL_msgCb(); test_wolfSSL_either_side(); test_wolfSSL_DTLS_either_side(); @@ -26665,13 +27729,20 @@ void ApiTest(void) test_wolfSSL_X509_STORE_CTX_set_time(); test_wolfSSL_get0_param(); test_wolfSSL_X509_VERIFY_PARAM_set1_host(); + test_wolfSSL_X509_STORE_CTX_get0_store(); test_wolfSSL_X509_STORE(); + test_wolfSSL_X509_STORE_load_locations(); test_wolfSSL_BN(); test_wolfSSL_PEM_read_bio(); test_wolfSSL_BIO(); test_wolfSSL_ASN1_STRING(); test_wolfSSL_X509(); test_wolfSSL_X509_VERIFY_PARAM(); + test_wolfSSL_X509_sign(); + test_wolfSSL_X509_get0_tbs_sigalg(); + test_wolfSSL_X509_ALGOR_get0(); + test_wolfSSL_X509_get_X509_PUBKEY(); + test_wolfSSL_X509_PUBKEY_get0_param(); test_wolfSSL_RAND(); test_wolfSSL_BUF(); test_wolfSSL_set_tlsext_status_type(); @@ -26685,19 +27756,30 @@ void ApiTest(void) test_wolfSSL_PKCS8_Compat(); test_wolfSSL_PKCS8_d2i(); test_wolfSSL_ERR_put_error(); + test_wolfSSL_ERR_print_errors(); test_wolfSSL_HMAC(); test_wolfSSL_OBJ(); test_wolfSSL_i2a_ASN1_OBJECT(); + test_wolfSSL_OBJ_cmp(); + test_wolfSSL_OBJ_txt2nid(); + test_wolfSSL_OBJ_txt2obj(); test_wolfSSL_X509_NAME_ENTRY(); + test_wolfSSL_X509_set_name(); + test_wolfSSL_X509_set_notAfter(); + test_wolfSSL_X509_set_notBefore(); + test_wolfSSL_X509_set_version(); test_wolfSSL_BIO_gets(); + test_wolfSSL_BIO_puts(); test_wolfSSL_d2i_PUBKEY(); test_wolfSSL_BIO_write(); + test_wolfSSL_BIO_printf(); test_wolfSSL_SESSION(); test_wolfSSL_DES_ecb_encrypt(); test_wolfSSL_sk_GENERAL_NAME(); test_wolfSSL_MD4(); test_wolfSSL_RSA(); test_wolfSSL_RSA_DER(); + test_wolfSSL_RSA_get0_key(); test_wolfSSL_verify_depth(); test_wolfSSL_HMAC_CTX(); test_wolfSSL_msg_callback(); @@ -26710,6 +27792,8 @@ void ApiTest(void) test_wolfSSL_X509_CRL(); test_wolfSSL_PEM_read_X509(); test_wolfSSL_PEM_read(); + test_wolfSSL_PEM_X509_INFO_read_bio(); + test_wolfSSL_PEM_read_bio_ECPKParameters(); test_wolfSSL_X509_NAME_ENTRY_get_object(); test_wolfSSL_OpenSSL_add_all_algorithms(); test_wolfSSL_ASN1_STRING_print_ex(); @@ -26721,6 +27805,9 @@ void ApiTest(void) test_wolfSSL_DES_ncbc(); test_wolfSSL_AES_cbc_encrypt(); test_wolfssl_EVP_aes_gcm(); + test_wolfSSL_PKEY_up_ref(); + test_wolfSSL_i2d_PrivateKey(); + test_wolfSSL_OCSP_get0_info(); #if (defined(OPENSSL_ALL) || defined(WOLFSSL_ASIO)) && !defined(NO_RSA) AssertIntEQ(test_wolfSSL_CTX_use_certificate_ASN1(), WOLFSSL_SUCCESS); diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 84a398fbc..f8185f0a1 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -1468,6 +1468,12 @@ static const byte pbeSha1Des3[] = {42, 134, 72, 134, 247, 13, 1, 12, 1, 3}; /* zlib compression */ static const byte zlibCompress[] = {42, 134, 72, 134, 247, 13, 1, 9, 16, 3, 8}; #endif +#ifdef WOLFSSL_APACHE_HTTPD +/* tlsExtType */ +static const byte tlsFeatureOid[] = {43, 6, 1, 5, 5, 7, 1, 24}; +/* certNameType */ +static const byte dnsSRVOid[] = {43, 6, 1, 5, 5, 7, 8, 7}; +#endif /* returns a pointer to the OID string on success and NULL on fail */ @@ -2015,7 +2021,24 @@ const byte* OidFromId(word32 id, word32 type, word32* oidSz) } break; #endif /* HAVE_LIBZ */ - +#ifdef WOLFSSL_APACHE_HTTPD + case oidCertNameType: + switch (id) { + case NID_id_on_dnsSRV: + oid = dnsSRVOid; + *oidSz = sizeof(dnsSRVOid); + break; + } + break; + case oidTlsExtType: + switch (id) { + case TLS_FEATURE_OID: + oid = tlsFeatureOid; + *oidSz = sizeof(tlsFeatureOid); + break; + } + break; +#endif /* WOLFSSL_APACHE_HTTPD */ case oidIgnoreType: default: break; @@ -8138,14 +8161,14 @@ static int CheckCertSignature_ex(const byte* cert, word32 certSz, void* heap, int len; word32 tbsCertIdx = 0; word32 sigIndex = 0; - word32 signatureOID; - word32 oid; + word32 signatureOID = 0; + word32 oid = 0; word32 issuerIdx = 0; word32 issuerSz = 0; #ifndef NO_SKID - int extLen; - word32 extIdx; - word32 extEndIdx; + int extLen = 0; + word32 extIdx = 0; + word32 extEndIdx = 0; int extAuthKeyIdSet = 0; #endif int ret = 0; @@ -15348,6 +15371,16 @@ void FreeOcspRequest(OcspRequest* req) XFREE(req->serial, req->heap, DYNAMIC_TYPE_OCSP_REQUEST); req->serial = NULL; +#ifdef OPENSSL_EXTRA + if (req->serialInt) { + if (req->serialInt->isDynamic) { + XFREE(req->serialInt->data, NULL, DYNAMIC_TYPE_OPENSSL); + } + XFREE(req->serialInt, NULL, DYNAMIC_TYPE_OPENSSL); + } + req->serialInt = NULL; +#endif + if (req->url) XFREE(req->url, req->heap, DYNAMIC_TYPE_OCSP_REQUEST); req->url = NULL; diff --git a/wolfcrypt/src/evp.c b/wolfcrypt/src/evp.c index 46faf75a9..f996c3bf0 100644 --- a/wolfcrypt/src/evp.c +++ b/wolfcrypt/src/evp.c @@ -82,7 +82,7 @@ int wolfSSL_EVP_Cipher_key_length(const WOLFSSL_EVP_CIPHER* c) } -WOLFSSL_API int wolfSSL_EVP_EncryptInit(WOLFSSL_EVP_CIPHER_CTX* ctx, +int wolfSSL_EVP_EncryptInit(WOLFSSL_EVP_CIPHER_CTX* ctx, const WOLFSSL_EVP_CIPHER* type, const unsigned char* key, const unsigned char* iv) @@ -90,7 +90,7 @@ WOLFSSL_API int wolfSSL_EVP_EncryptInit(WOLFSSL_EVP_CIPHER_CTX* ctx, return wolfSSL_EVP_CipherInit(ctx, type, (byte*)key, (byte*)iv, 1); } -WOLFSSL_API int wolfSSL_EVP_EncryptInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, +int wolfSSL_EVP_EncryptInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, const WOLFSSL_EVP_CIPHER* type, WOLFSSL_ENGINE *impl, const unsigned char* key, @@ -100,7 +100,7 @@ WOLFSSL_API int wolfSSL_EVP_EncryptInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, return wolfSSL_EVP_CipherInit(ctx, type, (byte*)key, (byte*)iv, 1); } -WOLFSSL_API int wolfSSL_EVP_DecryptInit(WOLFSSL_EVP_CIPHER_CTX* ctx, +int wolfSSL_EVP_DecryptInit(WOLFSSL_EVP_CIPHER_CTX* ctx, const WOLFSSL_EVP_CIPHER* type, const unsigned char* key, const unsigned char* iv) @@ -109,7 +109,7 @@ WOLFSSL_API int wolfSSL_EVP_DecryptInit(WOLFSSL_EVP_CIPHER_CTX* ctx, return wolfSSL_EVP_CipherInit(ctx, type, (byte*)key, (byte*)iv, 0); } -WOLFSSL_API int wolfSSL_EVP_DecryptInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, +int wolfSSL_EVP_DecryptInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, const WOLFSSL_EVP_CIPHER* type, WOLFSSL_ENGINE *impl, const unsigned char* key, @@ -121,7 +121,7 @@ WOLFSSL_API int wolfSSL_EVP_DecryptInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, } -WOLFSSL_API WOLFSSL_EVP_CIPHER_CTX *wolfSSL_EVP_CIPHER_CTX_new(void) +WOLFSSL_EVP_CIPHER_CTX *wolfSSL_EVP_CIPHER_CTX_new(void) { WOLFSSL_EVP_CIPHER_CTX *ctx = (WOLFSSL_EVP_CIPHER_CTX*)XMALLOC(sizeof *ctx, NULL, DYNAMIC_TYPE_TMP_BUFFER); @@ -132,7 +132,7 @@ WOLFSSL_API WOLFSSL_EVP_CIPHER_CTX *wolfSSL_EVP_CIPHER_CTX_new(void) return ctx; } -WOLFSSL_API void wolfSSL_EVP_CIPHER_CTX_free(WOLFSSL_EVP_CIPHER_CTX *ctx) +void wolfSSL_EVP_CIPHER_CTX_free(WOLFSSL_EVP_CIPHER_CTX *ctx) { if (ctx) { WOLFSSL_ENTER("wolfSSL_EVP_CIPHER_CTX_free"); @@ -141,13 +141,13 @@ WOLFSSL_API void wolfSSL_EVP_CIPHER_CTX_free(WOLFSSL_EVP_CIPHER_CTX *ctx) } } -WOLFSSL_API unsigned long wolfSSL_EVP_CIPHER_CTX_mode(const WOLFSSL_EVP_CIPHER_CTX *ctx) +unsigned long wolfSSL_EVP_CIPHER_CTX_mode(const WOLFSSL_EVP_CIPHER_CTX *ctx) { if (ctx == NULL) return 0; return ctx->flags & WOLFSSL_EVP_CIPH_MODE; } -WOLFSSL_API int wolfSSL_EVP_EncryptFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, +int wolfSSL_EVP_EncryptFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl) { if (ctx && ctx->enc) { @@ -159,7 +159,7 @@ WOLFSSL_API int wolfSSL_EVP_EncryptFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, } -WOLFSSL_API int wolfSSL_EVP_CipherInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, +int wolfSSL_EVP_CipherInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, const WOLFSSL_EVP_CIPHER* type, WOLFSSL_ENGINE *impl, const unsigned char* key, @@ -170,7 +170,7 @@ WOLFSSL_API int wolfSSL_EVP_CipherInit_ex(WOLFSSL_EVP_CIPHER_CTX* ctx, return wolfSSL_EVP_CipherInit(ctx, type, key, iv, enc); } -WOLFSSL_API int wolfSSL_EVP_EncryptFinal_ex(WOLFSSL_EVP_CIPHER_CTX *ctx, +int wolfSSL_EVP_EncryptFinal_ex(WOLFSSL_EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl) { if (ctx && ctx->enc) { @@ -181,7 +181,7 @@ WOLFSSL_API int wolfSSL_EVP_EncryptFinal_ex(WOLFSSL_EVP_CIPHER_CTX *ctx, return WOLFSSL_FAILURE; } -WOLFSSL_API int wolfSSL_EVP_DecryptFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, +int wolfSSL_EVP_DecryptFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl) { if (ctx && ctx->enc) { @@ -193,7 +193,7 @@ WOLFSSL_API int wolfSSL_EVP_DecryptFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, } } -WOLFSSL_API int wolfSSL_EVP_DecryptFinal_ex(WOLFSSL_EVP_CIPHER_CTX *ctx, +int wolfSSL_EVP_DecryptFinal_ex(WOLFSSL_EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl) { if (ctx && ctx->enc) { @@ -206,7 +206,7 @@ WOLFSSL_API int wolfSSL_EVP_DecryptFinal_ex(WOLFSSL_EVP_CIPHER_CTX *ctx, } -WOLFSSL_API int wolfSSL_EVP_DigestInit_ex(WOLFSSL_EVP_MD_CTX* ctx, +int wolfSSL_EVP_DigestInit_ex(WOLFSSL_EVP_MD_CTX* ctx, const WOLFSSL_EVP_MD* type, WOLFSSL_ENGINE *impl) { @@ -485,7 +485,7 @@ static int checkPad(WOLFSSL_EVP_CIPHER_CTX *ctx, unsigned char *buff) return ctx->block_size - n; } -WOLFSSL_API int wolfSSL_EVP_CipherFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, +int wolfSSL_EVP_CipherFinal(WOLFSSL_EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl) { int fl; @@ -607,7 +607,7 @@ WOLFSSL_API int wolfSSL_EVP_DecryptFinal_legacy(WOLFSSL_EVP_CIPHER_CTX *ctx, #endif -WOLFSSL_API int wolfSSL_EVP_CIPHER_CTX_block_size(const WOLFSSL_EVP_CIPHER_CTX *ctx) +int wolfSSL_EVP_CIPHER_CTX_block_size(const WOLFSSL_EVP_CIPHER_CTX *ctx) { if (ctx == NULL) return BAD_FUNC_ARG; switch (ctx->cipherType) { @@ -722,7 +722,7 @@ static unsigned int cipherType(const WOLFSSL_EVP_CIPHER *cipher) else return 0; } -WOLFSSL_API int wolfSSL_EVP_CIPHER_block_size(const WOLFSSL_EVP_CIPHER *cipher) +int wolfSSL_EVP_CIPHER_block_size(const WOLFSSL_EVP_CIPHER *cipher) { if (cipher == NULL) return BAD_FUNC_ARG; switch (cipherType(cipher)) { @@ -807,33 +807,33 @@ unsigned long WOLFSSL_CIPHER_mode(const WOLFSSL_EVP_CIPHER *cipher) } } -WOLFSSL_API unsigned long WOLFSSL_EVP_CIPHER_mode(const WOLFSSL_EVP_CIPHER *cipher) +unsigned long WOLFSSL_EVP_CIPHER_mode(const WOLFSSL_EVP_CIPHER *cipher) { if (cipher == NULL) return 0; return WOLFSSL_CIPHER_mode(cipher); } -WOLFSSL_API void wolfSSL_EVP_CIPHER_CTX_set_flags(WOLFSSL_EVP_CIPHER_CTX *ctx, int flags) +void wolfSSL_EVP_CIPHER_CTX_set_flags(WOLFSSL_EVP_CIPHER_CTX *ctx, int flags) { if (ctx != NULL) { ctx->flags |= flags; } } -WOLFSSL_API void wolfSSL_EVP_CIPHER_CTX_clear_flags(WOLFSSL_EVP_CIPHER_CTX *ctx, int flags) +void wolfSSL_EVP_CIPHER_CTX_clear_flags(WOLFSSL_EVP_CIPHER_CTX *ctx, int flags) { if (ctx != NULL) { ctx->flags &= ~flags; } } -WOLFSSL_API unsigned long wolfSSL_EVP_CIPHER_flags(const WOLFSSL_EVP_CIPHER *cipher) +unsigned long wolfSSL_EVP_CIPHER_flags(const WOLFSSL_EVP_CIPHER *cipher) { if (cipher == NULL) return 0; return WOLFSSL_CIPHER_mode(cipher); } -WOLFSSL_API int wolfSSL_EVP_CIPHER_CTX_set_padding(WOLFSSL_EVP_CIPHER_CTX *ctx, int padding) +int wolfSSL_EVP_CIPHER_CTX_set_padding(WOLFSSL_EVP_CIPHER_CTX *ctx, int padding) { if (ctx == NULL) return BAD_FUNC_ARG; if (padding) { @@ -845,7 +845,7 @@ WOLFSSL_API int wolfSSL_EVP_CIPHER_CTX_set_padding(WOLFSSL_EVP_CIPHER_CTX *ctx, return 1; } -WOLFSSL_API int wolfSSL_EVP_add_digest(const WOLFSSL_EVP_MD *digest) +int wolfSSL_EVP_add_digest(const WOLFSSL_EVP_MD *digest) { (void)digest; /* nothing to do */ @@ -857,7 +857,7 @@ WOLFSSL_API int wolfSSL_EVP_add_digest(const WOLFSSL_EVP_MD *digest) * * return WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_free(WOLFSSL_EVP_PKEY_CTX *ctx) +int wolfSSL_EVP_PKEY_CTX_free(WOLFSSL_EVP_PKEY_CTX *ctx) { if (ctx == NULL) return 0; WOLFSSL_ENTER("EVP_PKEY_CTX_free"); @@ -873,7 +873,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_free(WOLFSSL_EVP_PKEY_CTX *ctx) * * return the new structure on success and NULL if failed. */ -WOLFSSL_API WOLFSSL_EVP_PKEY_CTX *wolfSSL_EVP_PKEY_CTX_new(WOLFSSL_EVP_PKEY *pkey, WOLFSSL_ENGINE *e) +WOLFSSL_EVP_PKEY_CTX *wolfSSL_EVP_PKEY_CTX_new(WOLFSSL_EVP_PKEY *pkey, WOLFSSL_ENGINE *e) { WOLFSSL_EVP_PKEY_CTX* ctx; @@ -901,7 +901,7 @@ WOLFSSL_API WOLFSSL_EVP_PKEY_CTX *wolfSSL_EVP_PKEY_CTX_new(WOLFSSL_EVP_PKEY *pke * * returns WOLFSSL_SUCCESS on success. */ -WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_set_rsa_padding(WOLFSSL_EVP_PKEY_CTX *ctx, int padding) +int wolfSSL_EVP_PKEY_CTX_set_rsa_padding(WOLFSSL_EVP_PKEY_CTX *ctx, int padding) { if (ctx == NULL) return 0; WOLFSSL_ENTER("EVP_PKEY_CTX_set_rsa_padding"); @@ -909,6 +909,33 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_set_rsa_padding(WOLFSSL_EVP_PKEY_CTX *ctx, return WOLFSSL_SUCCESS; } +/* create a PKEY contxt and return it */ +WOLFSSL_EVP_PKEY_CTX *wolfSSL_EVP_PKEY_CTX_new_id(int id, WOLFSSL_ENGINE *e) +{ + WOLFSSL_EVP_PKEY* pkey; + WOLFSSL_EVP_PKEY_CTX* ctx = NULL; + + WOLFSSL_ENTER("wolfSSL_EVP_PKEY_CTX_new_id"); + + pkey = wolfSSL_PKEY_new_ex(NULL); + if (pkey) { + pkey->type = id; + ctx = wolfSSL_EVP_PKEY_CTX_new(pkey, e); + if (ctx == NULL) { + wolfSSL_EVP_PKEY_free(pkey); + } + } + return ctx; +} + +/* Returns WOLFSSL_SUCCESS or error */ +int wolfSSL_EVP_PKEY_CTX_set_rsa_keygen_bits(WOLFSSL_EVP_PKEY_CTX *ctx, int bits) +{ + if (ctx) { + ctx->nbits = bits; + } + return WOLFSSL_SUCCESS; +} /* Uses the WOLFSSL_EVP_PKEY_CTX to decrypt a buffer. * @@ -920,7 +947,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_set_rsa_padding(WOLFSSL_EVP_PKEY_CTX *ctx, * * returns WOLFSSL_SUCCESS on success. */ -WOLFSSL_API int wolfSSL_EVP_PKEY_decrypt(WOLFSSL_EVP_PKEY_CTX *ctx, +int wolfSSL_EVP_PKEY_decrypt(WOLFSSL_EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen) { @@ -963,7 +990,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_decrypt(WOLFSSL_EVP_PKEY_CTX *ctx, * * Returns WOLFSSL_FAILURE on failure and WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_PKEY_decrypt_init(WOLFSSL_EVP_PKEY_CTX *ctx) +int wolfSSL_EVP_PKEY_decrypt_init(WOLFSSL_EVP_PKEY_CTX *ctx) { if (ctx == NULL) return WOLFSSL_FAILURE; WOLFSSL_ENTER("EVP_PKEY_decrypt_init"); @@ -991,7 +1018,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_decrypt_init(WOLFSSL_EVP_PKEY_CTX *ctx) * * Returns WOLFSSL_FAILURE on failure and WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_PKEY_encrypt(WOLFSSL_EVP_PKEY_CTX *ctx, +int wolfSSL_EVP_PKEY_encrypt(WOLFSSL_EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen) { @@ -1034,7 +1061,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_encrypt(WOLFSSL_EVP_PKEY_CTX *ctx, * * Returns WOLFSSL_FAILURE on failure and WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_PKEY_encrypt_init(WOLFSSL_EVP_PKEY_CTX *ctx) +int wolfSSL_EVP_PKEY_encrypt_init(WOLFSSL_EVP_PKEY_CTX *ctx) { if (ctx == NULL) return WOLFSSL_FAILURE; WOLFSSL_ENTER("EVP_PKEY_encrypt_init"); @@ -1131,7 +1158,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_sign(WOLFSSL_EVP_PKEY_CTX *ctx, unsigned char * * * returns the size in bits of key on success */ -WOLFSSL_API int wolfSSL_EVP_PKEY_bits(const WOLFSSL_EVP_PKEY *pkey) +int wolfSSL_EVP_PKEY_bits(const WOLFSSL_EVP_PKEY *pkey) { int bytes; @@ -1142,6 +1169,66 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_bits(const WOLFSSL_EVP_PKEY *pkey) } +int wolfSSL_EVP_PKEY_keygen_init(WOLFSSL_EVP_PKEY_CTX *ctx) +{ + (void)ctx; + return WOLFSSL_SUCCESS; +} + +int wolfSSL_EVP_PKEY_keygen(WOLFSSL_EVP_PKEY_CTX *ctx, + WOLFSSL_EVP_PKEY **ppkey) +{ + int ret = WOLFSSL_FAILURE; + int ownPkey = 0; + WOLFSSL_EVP_PKEY* pkey; + + if (ctx == NULL || ppkey == NULL) { + return BAD_FUNC_ARG; + } + + pkey = *ppkey; + if (pkey == NULL) { + ownPkey = 1; + pkey = wolfSSL_PKEY_new(); + } + + switch (pkey->type) { +#if !defined(NO_RSA) && !defined(HAVE_USER_RSA) + case EVP_PKEY_RSA: + pkey->rsa = wolfSSL_RSA_generate_key(ctx->nbits, WC_RSA_EXPONENT, + NULL, NULL); + if (pkey->rsa) { + pkey->ownRsa = 1; + pkey->pkey_sz = wolfSSL_i2d_RSAPrivateKey(pkey->rsa, + (unsigned char**)&pkey->pkey.ptr); + ret = WOLFSSL_SUCCESS; + } + break; +#endif +#ifdef HAVE_ECC + case EVP_PKEY_EC: + pkey->ecc = wolfSSL_EC_KEY_new(); + if (pkey->ecc) { + ret = wolfSSL_EC_KEY_generate_key(pkey->ecc); + if (ret == WOLFSSL_SUCCESS) { + pkey->ownEcc = 1; + } + } +#endif + default: + break; + } + + if (ret != WOLFSSL_SUCCESS && ownPkey) { + wolfSSL_EVP_PKEY_free(pkey); + pkey = NULL; + } + + *ppkey = pkey; + + return ret; +} + /* Get the size in bytes for WOLFSSL_EVP_PKEY key * * pkey WOLFSSL_EVP_PKEY structure to get key size of @@ -1149,7 +1236,7 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_bits(const WOLFSSL_EVP_PKEY *pkey) * returns the size of a key on success which is the maximum size of a * signature */ -WOLFSSL_API int wolfSSL_EVP_PKEY_size(WOLFSSL_EVP_PKEY *pkey) +int wolfSSL_EVP_PKEY_size(WOLFSSL_EVP_PKEY *pkey) { if (pkey == NULL) return 0; WOLFSSL_ENTER("EVP_PKEY_size"); @@ -1183,13 +1270,22 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_size(WOLFSSL_EVP_PKEY *pkey) * * returns WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_SignInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EVP_MD *type) +int wolfSSL_EVP_SignInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EVP_MD *type) { if (ctx == NULL) return WOLFSSL_FAILURE; WOLFSSL_ENTER("EVP_SignInit"); return wolfSSL_EVP_DigestInit(ctx,type); } +WOLFSSL_API int wolfSSL_EVP_SignInit_ex(WOLFSSL_EVP_MD_CTX* ctx, + const WOLFSSL_EVP_MD* type, + WOLFSSL_ENGINE *impl) +{ + if (ctx == NULL) return WOLFSSL_FAILURE; + WOLFSSL_ENTER("EVP_SignInit"); + return wolfSSL_EVP_DigestInit_ex(ctx,type,impl); +} + /* Update structure with data for signing * @@ -1199,7 +1295,7 @@ WOLFSSL_API int wolfSSL_EVP_SignInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EVP_ * * returns WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_SignUpdate(WOLFSSL_EVP_MD_CTX *ctx, const void *data, size_t len) +int wolfSSL_EVP_SignUpdate(WOLFSSL_EVP_MD_CTX *ctx, const void *data, size_t len) { if (ctx == NULL) return 0; WOLFSSL_ENTER("EVP_SignUpdate("); @@ -1248,7 +1344,7 @@ static int md2nid(const unsigned char md) * * returns WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE on failure */ -WOLFSSL_API int wolfSSL_EVP_SignFinal(WOLFSSL_EVP_MD_CTX *ctx, unsigned char *sigret, +int wolfSSL_EVP_SignFinal(WOLFSSL_EVP_MD_CTX *ctx, unsigned char *sigret, unsigned int *siglen, WOLFSSL_EVP_PKEY *pkey) { unsigned int mdsize; @@ -1291,7 +1387,7 @@ WOLFSSL_API int wolfSSL_EVP_SignFinal(WOLFSSL_EVP_MD_CTX *ctx, unsigned char *si * * returns WOLFSSL_SUCCESS on success */ -WOLFSSL_API int wolfSSL_EVP_VerifyInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EVP_MD *type) +int wolfSSL_EVP_VerifyInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EVP_MD *type) { if (ctx == NULL) return WOLFSSL_FAILURE; WOLFSSL_ENTER("EVP_VerifyInit"); @@ -1307,7 +1403,7 @@ WOLFSSL_API int wolfSSL_EVP_VerifyInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EV * * returns WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE on failure */ -WOLFSSL_API int wolfSSL_EVP_VerifyUpdate(WOLFSSL_EVP_MD_CTX *ctx, const void *data, size_t len) +int wolfSSL_EVP_VerifyUpdate(WOLFSSL_EVP_MD_CTX *ctx, const void *data, size_t len) { if (ctx == NULL) return WOLFSSL_FAILURE; WOLFSSL_ENTER("EVP_VerifyUpdate"); @@ -1324,7 +1420,7 @@ WOLFSSL_API int wolfSSL_EVP_VerifyUpdate(WOLFSSL_EVP_MD_CTX *ctx, const void *da * * returns WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE on failure */ -WOLFSSL_API int wolfSSL_EVP_VerifyFinal(WOLFSSL_EVP_MD_CTX *ctx, +int wolfSSL_EVP_VerifyFinal(WOLFSSL_EVP_MD_CTX *ctx, unsigned char*sig, unsigned int siglen, WOLFSSL_EVP_PKEY *pkey) { int ret; @@ -1359,7 +1455,7 @@ WOLFSSL_API int wolfSSL_EVP_VerifyFinal(WOLFSSL_EVP_MD_CTX *ctx, return WOLFSSL_FAILURE; } -WOLFSSL_API int wolfSSL_EVP_add_cipher(const WOLFSSL_EVP_CIPHER *cipher) +int wolfSSL_EVP_add_cipher(const WOLFSSL_EVP_CIPHER *cipher) { (void)cipher; /* nothing to do */ @@ -1798,10 +1894,84 @@ int wolfSSL_EVP_DigestVerifyFinal(WOLFSSL_EVP_MD_CTX *ctx, return WOLFSSL_FAILURE; } + +#ifdef WOLFSSL_APACHE_HTTPD +#if !defined(USE_WINDOWS_API) && !defined(MICROCHIP_PIC32) + #include +#endif + +#ifndef XGETPASSWD + static int XGETPASSWD(char* buf, int bufSz) { + int ret = WOLFSSL_SUCCESS; + + /* turn off echo for passwords */ + #ifdef USE_WINDOWS_API + DWORD originalTerm; + DWORD newTerm; + CONSOLE_SCREEN_BUFFER_INFO screenOrig; + HANDLE stdinHandle = GetStdHandle(STD_INPUT_HANDLE); + if (GetConsoleMode(stdinHandle, &originalTerm) == 0) { + WOLFSSL_MSG("Couldn't get the original terminal settings"); + return WOLFSSL_FAILURE; + } + newTerm = originalTerm; + newTerm &= ~ENABLE_ECHO_INPUT; + if (SetConsoleMode(stdinHandle, newTerm) == 0) { + WOLFSSL_MSG("Couldn't turn off echo"); + return WOLFSSL_FAILURE; + } + #else + struct termios originalTerm; + struct termios newTerm; + if (tcgetattr(STDIN_FILENO, &originalTerm) != 0) { + WOLFSSL_MSG("Couldn't get the original terminal settings"); + return WOLFSSL_FAILURE; + } + XMEMCPY(&newTerm, &originalTerm, sizeof(struct termios)); + + newTerm.c_lflag &= ~ECHO; + newTerm.c_lflag |= (ICANON | ECHONL); + if (tcsetattr(STDIN_FILENO, TCSANOW, &newTerm) != 0) { + WOLFSSL_MSG("Couldn't turn off echo"); + return WOLFSSL_FAILURE; + } + #endif + + if (XFGETS(buf, bufSz, stdin) == NULL) { + ret = WOLFSSL_FAILURE; + } + + /* restore default echo */ + #ifdef USE_WINDOWS_API + if (SetConsoleMode(stdinHandle, originalTerm) == 0) { + WOLFSSL_MSG("Couldn't restore the terminal settings"); + return WOLFSSL_FAILURE; + } + #else + if (tcsetattr(STDIN_FILENO, TCSANOW, &originalTerm) != 0) { + WOLFSSL_MSG("Couldn't restore the terminal settings"); + return WOLFSSL_FAILURE; + } + #endif + return ret; + } +#endif + +/* returns 0 on success and -2 or -1 on failure */ +int wolfSSL_EVP_read_pw_string(char* buf, int bufSz, const char* banner, int v) +{ + printf("%s", banner); + if (XGETPASSWD(buf, bufSz) == WOLFSSL_FAILURE) { + return -1; + } + (void)v; /* fgets always sanity checks size of input vs buffer */ + return 0; +} +#endif /* WOLFSSL_APACHE_HTTPD */ #endif /* WOLFSSL_EVP_INCLUDED */ #if defined(OPENSSL_EXTRA) && !defined(NO_PWDBASED) && !defined(NO_SHA) -WOLFSSL_API int wolfSSL_PKCS5_PBKDF2_HMAC_SHA1(const char *pass, int passlen, +int wolfSSL_PKCS5_PBKDF2_HMAC_SHA1(const char *pass, int passlen, const unsigned char *salt, int saltlen, int iter, int keylen, unsigned char *out) diff --git a/wolfcrypt/src/logging.c b/wolfcrypt/src/logging.c index 318a883b5..d86a727c1 100644 --- a/wolfcrypt/src/logging.c +++ b/wolfcrypt/src/logging.c @@ -355,9 +355,10 @@ void WOLFSSL_LEAVE(const char* msg, int ret) * name where WOLFSSL_ERROR is called at. */ #if defined(DEBUG_WOLFSSL) || defined(OPENSSL_ALL) || \ - defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) + defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) || \ + defined(OPENSSL_EXTRA) -#if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) +#if (defined(OPENSSL_EXTRA) && !defined(_WIN32)) || defined(DEBUG_WOLFSSL_VERBOSE) void WOLFSSL_ERROR_LINE(int error, const char* func, unsigned int line, const char* file, void* usrCtx) #else @@ -370,7 +371,7 @@ void WOLFSSL_ERROR(int error) { char buffer[WOLFSSL_MAX_ERROR_SZ]; - #if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) + #if (defined(OPENSSL_EXTRA) && !defined(_WIN32)) || defined(DEBUG_WOLFSSL_VERBOSE) (void)usrCtx; /* a user ctx for future flexibility */ (void)func; @@ -484,11 +485,6 @@ int wc_PeekErrorNode(int idx, const char **file, const char **reason, if (idx < 0) { err = wc_last_node; - if (err == NULL) { - WOLFSSL_MSG("No Errors in queue"); - wc_UnLockMutex(&debug_mutex); - return BAD_STATE_E; - } } else { int i; @@ -504,6 +500,12 @@ int wc_PeekErrorNode(int idx, const char **file, const char **reason, } } + if (err == NULL) { + WOLFSSL_MSG("No Errors in queue"); + wc_UnLockMutex(&debug_mutex); + return BAD_STATE_E; + } + if (file != NULL) { *file = err->file; } @@ -669,10 +671,14 @@ void wc_RemoveErrorNode(int idx) if (current != NULL) { if (current->prev != NULL) current->prev->next = current->next; + if (current->next != NULL) + current->next->prev = current->prev; if (wc_last_node == current) wc_last_node = current->prev; if (wc_errors == current) wc_errors = current->next; + if (wc_current_node == current) + wc_current_node = current->next; XFREE(current, current->heap, DYNAMIC_TYPE_LOG); } diff --git a/wolfssl/error-ssl.h b/wolfssl/error-ssl.h index bc433ef92..864d67b8e 100644 --- a/wolfssl/error-ssl.h +++ b/wolfssl/error-ssl.h @@ -164,6 +164,7 @@ enum wolfSSL_ErrorCodes { TCA_INVALID_ID_TYPE = -433, /* TLSX TCA ID type invalid */ TCA_ABSENT_ERROR = -434, /* TLSX TCA ID no response */ TSIP_MAC_DIGSZ_E = -435, /* Invalid MAC size for TSIP */ + CLIENT_CERT_CB_ERROR = -436, /* Client cert callback error */ /* add strings to wolfSSL_ERR_reason_error_string in internal.c !!!!! */ /* begin negotiation parameter errors */ diff --git a/wolfssl/internal.h b/wolfssl/internal.h index a5cbf5e12..56509903e 100644 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -1433,10 +1433,6 @@ enum Misc { MAX_WOLFSSL_FILE_SIZE = 1024ul * 1024ul * 4, /* 4 mb file size alloc limit */ -#if defined(HAVE_EX_DATA) || defined(FORTRESS) - MAX_EX_DATA = 5, /* allow for five items of ex_data */ -#endif - MAX_X509_SIZE = 2048, /* max static x509 buffer size */ CERT_MIN_SIZE = 256, /* min PEM cert size with header/footer */ @@ -1616,15 +1612,35 @@ WOLFSSL_LOCAL ProtocolVersion MakeTLSv1_3(void); #endif + +/* custom method with user set callbacks */ +#define MAX_BIO_METHOD_NAME 256 +typedef struct WOLFSSL_BIO_METHOD_CUSTOM { + char name[MAX_BIO_METHOD_NAME]; + + wolfSSL_BIO_meth_puts_cb putsCb; + wolfSSL_BIO_meth_gets_cb getsCb; + + wolfSSL_BIO_meth_read_cb readCb; + wolfSSL_BIO_meth_write_cb writeCb; + + wolfSSL_BIO_meth_destroy_cb freeCb; + wolfSSL_BIO_meth_create_cb createCb; + + wolfSSL_BIO_meth_get_ctrl_cb ctrlCb; +} WOLFSSL_BIO_METHOD_CUSTOM; + /* wolfSSL BIO_METHOD type */ struct WOLFSSL_BIO_METHOD { byte type; /* method type */ + WOLFSSL_BIO_METHOD_CUSTOM* custom; }; /* wolfSSL BIO type */ struct WOLFSSL_BIO { WOLFSSL_BUF_MEM* mem_buf; + WOLFSSL_BIO_METHOD* method; WOLFSSL* ssl; /* possible associated ssl */ #ifndef NO_FILESYSTEM XFILE file; @@ -1634,6 +1650,9 @@ struct WOLFSSL_BIO { WOLFSSL_BIO* pair; /* BIO paired with */ void* heap; /* user heap hint */ byte* mem; /* memory buffer */ + void* usrCtx; /* user set pointer */ + char* infoArg; /* BIO callback argument */ + wolf_bio_info_cb infoCb; /* BIO callback */ int wrSz; /* write buffer size (mem) */ int wrIdx; /* current index for write buffer */ int rdIdx; /* current read index */ @@ -1696,6 +1715,7 @@ WOLFSSL_LOCAL int GetPrivateKeySigSize(WOLFSSL* ssl); #endif #endif WOLFSSL_LOCAL void FreeKeyExchange(WOLFSSL* ssl); +WOLFSSL_LOCAL void FreeSuites(WOLFSSL* ssl); WOLFSSL_LOCAL int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx, word32 size); WOLFSSL_LOCAL int MatchDomainName(const char* pattern, int len, const char* str); #ifndef NO_CERTS @@ -1810,6 +1830,9 @@ struct Suites { byte setSuites; /* user set suites from default */ byte hashAlgo; /* selected hash algorithm */ byte sigAlgo; /* selected sig algorithm */ +#ifdef OPENSSL_ALL + WOLF_STACK_OF(WOLFSSL_CIPHER)* stack; /* stack of available cipher suites */ +#endif }; @@ -1844,6 +1867,8 @@ WOLFSSL_LOCAL int SetCipherList(WOLFSSL_CTX*, Suites*, const char* list); /* wolfSSL Cipher type just points back to SSL */ struct WOLFSSL_CIPHER { + byte cipherSuite0; + byte cipherSuite; WOLFSSL* ssl; }; @@ -2368,6 +2393,7 @@ typedef struct SecureRenegotiation { enum key_cache_state cache_status; /* track key cache state */ byte client_verify_data[TLS_FINISHED_SZ]; /* cached */ byte server_verify_data[TLS_FINISHED_SZ]; /* cached */ + byte subject_hash_set; /* if peer cert hash is set */ byte subject_hash[KEYID_SIZE]; /* peer cert hash */ Keys tmp_keys; /* can't overwrite real keys yet */ } SecureRenegotiation; @@ -2579,6 +2605,7 @@ struct WOLFSSL_CTX { #if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA) || \ defined(WOLFSSL_NGINX) || defined (WOLFSSL_HAPROXY) WOLF_STACK_OF(WOLFSSL_X509)* x509Chain; + client_cert_cb CBClientCert; /* client certificate callback */ #endif #ifdef WOLFSSL_TLS13 int certChainCnt; @@ -3136,6 +3163,7 @@ enum ConnectState { /* server accept state for nonblocking restart */ enum AcceptState { ACCEPT_BEGIN = 0, + ACCEPT_BEGIN_RENEG, ACCEPT_CLIENT_HELLO_DONE, ACCEPT_HELLO_RETRY_REQUEST_DONE, ACCEPT_FIRST_REPLY_DONE, @@ -3157,6 +3185,7 @@ enum AcceptState { /* TLS 1.3 server accept state for nonblocking restart */ enum AcceptStateTls13 { TLS13_ACCEPT_BEGIN = 0, + TLS13_ACCEPT_BEGIN_RENEG, TLS13_ACCEPT_CLIENT_HELLO_DONE, TLS13_ACCEPT_HELLO_RETRY_REQUEST_DONE, TLS13_ACCEPT_FIRST_REPLY_DONE, @@ -3467,23 +3496,28 @@ typedef struct Arrays { #define STACK_TYPE_ACCESS_DESCRIPTION 6 #define STACK_TYPE_X509_EXT 7 #define STACK_TYPE_NULL 8 +#define STACK_TYPE_X509_NAME 9 struct WOLFSSL_STACK { unsigned long num; /* number of nodes in stack * (safety measure for freeing and shortcut for count) */ + #if defined(OPENSSL_ALL) + wolf_sk_compare_cb comp; + #endif union { WOLFSSL_X509* x509; WOLFSSL_X509_NAME* name; + WOLFSSL_X509_INFO* info; WOLFSSL_BIO* bio; WOLFSSL_ASN1_OBJECT* obj; - WOLFSSL_CIPHER* cipher; - #if defined(OPENSSL_ALL) || defined(WOLFSSL_QT) + WOLFSSL_CIPHER cipher; WOLFSSL_ACCESS_DESCRIPTION* access; WOLFSSL_X509_EXTENSION* ext; - #endif void* generic; char* string; + WOLFSSL_GENERAL_NAME* gn; } data; + void* heap; /* memory heap hint */ WOLFSSL_STACK* next; byte type; /* Identifies type of stack. */ }; @@ -3539,8 +3573,8 @@ struct WOLFSSL_X509 { #endif /* WOLFSSL_QT || OPENSSL_ALL */ int notBeforeSz; int notAfterSz; - byte notBefore[MAX_DATE_SZ]; - byte notAfter[MAX_DATE_SZ]; + WOLFSSL_ASN1_TIME notBefore; + WOLFSSL_ASN1_TIME notAfter; buffer sig; int sigOID; DNS_entry* altNames; /* alt names list */ @@ -3611,6 +3645,10 @@ struct WOLFSSL_X509 { #endif WOLFSSL_X509_NAME issuer; WOLFSSL_X509_NAME subject; +#if defined(OPENSSL_ALL) + WOLFSSL_X509_ALGOR algor; + WOLFSSL_X509_PUBKEY key; +#endif }; @@ -3993,6 +4031,7 @@ struct WOLFSSL { #endif #if defined(HAVE_SECURE_RENEGOTIATION) \ || defined(HAVE_SERVER_RENEGOTIATION_INFO) + int secure_rene_count; /* how many times */ SecureRenegotiation* secure_renegotiation; /* valid pointer indicates */ #endif /* user turned on */ #ifdef HAVE_ALPN @@ -4078,6 +4117,9 @@ struct WOLFSSL { EarlyDataState earlyData; word32 earlyDataSz; #endif +#ifdef OPENSSL_ALL + long verifyCallbackResult; +#endif }; diff --git a/wolfssl/ocsp.h b/wolfssl/ocsp.h index e49453633..1174a21bf 100644 --- a/wolfssl/ocsp.h +++ b/wolfssl/ocsp.h @@ -37,12 +37,15 @@ typedef struct WOLFSSL_OCSP WOLFSSL_OCSP; -#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) +#if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA) || defined(WOLFSSL_NGINX) ||\ + defined(WOLFSSL_HAPROXY) typedef struct OcspResponse WOLFSSL_OCSP_BASICRESP; typedef struct OcspRequest WOLFSSL_OCSP_CERTID; typedef struct OcspRequest WOLFSSL_OCSP_ONEREQ; + +typedef struct OcspRequest WOLFSSL_OCSP_REQUEST; #endif WOLFSSL_LOCAL int InitOCSP(WOLFSSL_OCSP*, WOLFSSL_CERT_MANAGER*); @@ -58,7 +61,8 @@ WOLFSSL_LOCAL int CheckOcspResponse(WOLFSSL_OCSP *ocsp, byte *response, int resp WOLFSSL_BUFFER_INFO *responseBuffer, CertStatus *status, OcspEntry *entry, OcspRequest *ocspRequest); -#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) +#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) || \ + defined(WOLFSSL_APACHE_HTTPD) WOLFSSL_API int wolfSSL_OCSP_resp_find_status(WOLFSSL_OCSP_BASICRESP *bs, WOLFSSL_OCSP_CERTID *id, int *status, int *reason, @@ -95,8 +99,27 @@ WOLFSSL_API int wolfSSL_i2d_OCSP_REQUEST(OcspRequest* request, unsigned char** data); WOLFSSL_API WOLFSSL_OCSP_ONEREQ* wolfSSL_OCSP_request_add0_id(OcspRequest *req, WOLFSSL_OCSP_CERTID *cid); +WOLFSSL_API WOLFSSL_OCSP_CERTID* wolfSSL_OCSP_CERTID_dup(WOLFSSL_OCSP_CERTID*); +WOLFSSL_API int wolfSSL_i2d_OCSP_REQUEST_bio(WOLFSSL_BIO* out, + WOLFSSL_OCSP_REQUEST *req); #endif +#ifdef OPENSSL_EXTRA +WOLFSSL_API int wolfSSL_OCSP_REQUEST_add_ext(OcspRequest* req, + WOLFSSL_X509_EXTENSION* ext, int idx); +WOLFSSL_API OcspResponse* wolfSSL_OCSP_response_create(int status, + WOLFSSL_OCSP_BASICRESP* bs); +WOLFSSL_API const char* wolfSSL_OCSP_crl_reason_str(long s); + +WOLFSSL_API int wolfSSL_OCSP_id_get0_info(WOLFSSL_ASN1_STRING**, + WOLFSSL_ASN1_OBJECT**, WOLFSSL_ASN1_STRING**, + WOLFSSL_ASN1_INTEGER**, WOLFSSL_OCSP_CERTID*); + +WOLFSSL_API int wolfSSL_OCSP_request_add1_nonce(OcspRequest* req, + unsigned char* val, int sz); +WOLFSSL_API int wolfSSL_OCSP_check_nonce(OcspRequest* req, + WOLFSSL_OCSP_BASICRESP* bs); +#endif #ifdef __cplusplus diff --git a/wolfssl/openssl/asn1.h b/wolfssl/openssl/asn1.h index 6500f6cd1..1e7ae266b 100644 --- a/wolfssl/openssl/asn1.h +++ b/wolfssl/openssl/asn1.h @@ -26,7 +26,7 @@ #include -#define ASN1_STRING_new wolfSSL_ASN1_STRING_type_new +#define ASN1_STRING_new wolfSSL_ASN1_STRING_new #define ASN1_STRING_type_new wolfSSL_ASN1_STRING_type_new #define ASN1_STRING_type wolfSSL_ASN1_STRING_type #define ASN1_STRING_set wolfSSL_ASN1_STRING_set @@ -56,5 +56,21 @@ ASN1_STRFLGS_DUMP_DER) #define MBSTRING_UTF8 0x1000 +#define MBSTRING_ASC 0x1001 +#define MBSTRING_BMP 0x1002 +#define MBSTRING_UNIV 0x1004 + +#define ASN1_UTCTIME_print wolfSSL_ASN1_UTCTIME_print +#define ASN1_TIME_check wolfSSL_ASN1_TIME_check +#define ASN1_TIME_diff wolfSSL_ASN1_TIME_diff +#define ASN1_TIME_set wolfSSL_ASN1_TIME_set + +#define V_ASN1_UTCTIME 23 +#define V_ASN1_GENERALIZEDTIME 24 + +WOLFSSL_API WOLFSSL_ASN1_INTEGER *wolfSSL_BN_to_ASN1_INTEGER( + const WOLFSSL_BIGNUM*, WOLFSSL_ASN1_INTEGER*); +#define BN_to_ASN1_INTEGER wolfSSL_BN_to_ASN1_INTEGER + #endif /* WOLFSSL_ASN1_H_ */ diff --git a/wolfssl/openssl/bio.h b/wolfssl/openssl/bio.h index b0992f9aa..20fbec424 100644 --- a/wolfssl/openssl/bio.h +++ b/wolfssl/openssl/bio.h @@ -41,16 +41,70 @@ #define BIO_find_type wolfSSL_BIO_find_type #define BIO_next wolfSSL_BIO_next #define BIO_gets wolfSSL_BIO_gets - +#define BIO_puts wolfSSL_BIO_puts #define BIO_TYPE_FILE WOLFSSL_BIO_FILE #define BIO_TYPE_BIO WOLFSSL_BIO_BIO #define BIO_TYPE_MEM WOLFSSL_BIO_MEMORY #define BIO_TYPE_BASE64 WOLFSSL_BIO_BASE64 +#define BIO_printf wolfSSL_BIO_printf +#define BIO_dump wolfSSL_BIO_dump + +/* BIO callback */ +#define BIO_CB_FREE WOLFSSL_BIO_CB_FREE +#define BIO_CB_READ WOLFSSL_BIO_CB_READ +#define BIO_CB_WRITE WOLFSSL_BIO_CB_WRITE +#define BIO_CB_PUTS WOLFSSL_BIO_CB_PUTS +#define BIO_CB_GETS WOLFSSL_BIO_CB_GETS +#define BIO_CB_CTRL WOLFSSL_BIO_CB_CTRL +#define BIO_CB_RETURN WOLFSSL_BIO_CB_RETURN + +#define BIO_set_callback wolfSSL_BIO_set_callback +#define BIO_get_callback wolfSSL_BIO_get_callback +#define BIO_set_callback_arg wolfSSL_BIO_set_callback_arg +#define BIO_get_callback_arg wolfSSL_BIO_get_callback_arg + +/* BIO for 1.1.0 or later */ +#define BIO_set_init wolfSSL_BIO_set_init +#define BIO_get_data wolfSSL_BIO_get_data +#define BIO_set_data wolfSSL_BIO_set_data +#define BIO_get_shutdown wolfSSL_BIO_get_shutdown +#define BIO_set_shutdown wolfSSL_BIO_set_shutdown + +/* helper to set specific retry/read flags */ +#define BIO_set_retry_read(bio)\ + wolfSSL_BIO_set_flags((bio), WOLFSSL_BIO_FLAG_RETRY | WOLFSSL_BIO_FLAG_READ) + +#define BIO_clear_retry_flags wolfSSL_BIO_clear_retry_flags + +#define BIO_meth_new wolfSSL_BIO_meth_new +#define BIO_meth_set_write wolfSSL_BIO_meth_set_write +#define BIO_meth_free wolfSSL_BIO_meth_free +#define BIO_meth_set_write wolfSSL_BIO_meth_set_write +#define BIO_meth_set_read wolfSSL_BIO_meth_set_read +#define BIO_meth_set_puts wolfSSL_BIO_meth_set_puts +#define BIO_meth_set_gets wolfSSL_BIO_meth_set_gets +#define BIO_meth_set_ctrl wolfSSL_BIO_meth_set_ctrl +#define BIO_meth_set_create wolfSSL_BIO_meth_set_create +#define BIO_meth_set_destroy wolfSSL_BIO_meth_set_destroy + + +/* BIO CTRL */ +#define BIO_CTRL_EOF 2 +#define BIO_CTRL_PUSH 6 +#define BIO_CTRL_POP 7 +#define BIO_CTRL_GET_CLOSE 8 +#define BIO_CTRL_SET_CLOSE 9 +#define BIO_CTRL_PENDING 10 +#define BIO_CTRL_DUP 12 + +#define BIO_C_SET_BUF_MEM 114 +#define BIO_C_GET_BUF_MEM_PTR 115 + #ifdef __cplusplus - } /* extern "C" */ + } /* extern "C" */ #endif diff --git a/wolfssl/openssl/bn.h b/wolfssl/openssl/bn.h index c5176813b..178f86bdf 100644 --- a/wolfssl/openssl/bn.h +++ b/wolfssl/openssl/bn.h @@ -125,6 +125,7 @@ WOLFSSL_API WOLFSSL_BIGNUM *wolfSSL_BN_CTX_get(WOLFSSL_BN_CTX *ctx); WOLFSSL_API void wolfSSL_BN_CTX_start(WOLFSSL_BN_CTX *ctx); WOLFSSL_API WOLFSSL_BIGNUM *wolfSSL_BN_mod_inverse(WOLFSSL_BIGNUM*, WOLFSSL_BIGNUM*, const WOLFSSL_BIGNUM*, WOLFSSL_BN_CTX *ctx); + typedef WOLFSSL_BIGNUM BIGNUM; typedef WOLFSSL_BN_CTX BN_CTX; typedef WOLFSSL_BN_GENCB BN_GENCB; @@ -190,6 +191,18 @@ typedef WOLFSSL_BN_GENCB BN_GENCB; #define BN_mod_inverse wolfSSL_BN_mod_inverse +#if defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x10100000L +#define BN_get_rfc2409_prime_768 wolfSSL_DH_768_prime +#define BN_get_rfc2409_prime_1024 wolfSSL_DH_1024_prime +#define BN_get_rfc3526_prime_1536 wolfSSL_DH_1536_prime +#define BN_get_rfc3526_prime_2048 wolfSSL_DH_2048_prime +#define BN_get_rfc3526_prime_3072 wolfSSL_DH_3072_prime +#define BN_get_rfc3526_prime_4096 wolfSSL_DH_4096_prime +#define BN_get_rfc3526_prime_6144 wolfSSL_DH_6144_prime +#define BN_get_rfc3526_prime_8192 wolfSSL_DH_8192_prime +#endif + + #ifdef __cplusplus } /* extern "C" */ #endif diff --git a/wolfssl/openssl/crypto.h b/wolfssl/openssl/crypto.h index 79a42dd61..81edb7597 100644 --- a/wolfssl/openssl/crypto.h +++ b/wolfssl/openssl/crypto.h @@ -46,13 +46,14 @@ WOLFSSL_API void *wolfSSL_OPENSSL_malloc(size_t a); #define SSLeay_version wolfSSLeay_version #define SSLeay wolfSSLeay +#define OpenSSL_version wolfSSLeay_version #define SSLEAY_VERSION 0x0090600fL #define SSLEAY_VERSION_NUMBER SSLEAY_VERSION #define CRYPTO_lock wc_LockMutex_ex /* this function was used to set the default malloc, free, and realloc */ -#define CRYPTO_malloc_init() /* CRYPTO_malloc_init is not needed */ +#define CRYPTO_malloc_init() 0 /* CRYPTO_malloc_init is not needed */ #define OPENSSL_free wolfSSL_OPENSSL_free #define OPENSSL_malloc wolfSSL_OPENSSL_malloc diff --git a/wolfssl/openssl/dh.h b/wolfssl/openssl/dh.h index 85c8c6ae9..f31c76aaf 100644 --- a/wolfssl/openssl/dh.h +++ b/wolfssl/openssl/dh.h @@ -55,6 +55,8 @@ WOLFSSL_API int wolfSSL_DH_size(WOLFSSL_DH*); WOLFSSL_API int wolfSSL_DH_generate_key(WOLFSSL_DH*); WOLFSSL_API int wolfSSL_DH_compute_key(unsigned char* key, WOLFSSL_BIGNUM* pub, WOLFSSL_DH*); +WOLFSSL_API int wolfSSL_DH_set0_pqg(WOLFSSL_DH*, WOLFSSL_BIGNUM*, + WOLFSSL_BIGNUM*, WOLFSSL_BIGNUM*); typedef WOLFSSL_DH DH; @@ -64,8 +66,20 @@ typedef WOLFSSL_DH DH; #define DH_size wolfSSL_DH_size #define DH_generate_key wolfSSL_DH_generate_key #define DH_compute_key wolfSSL_DH_compute_key -#define get_rfc3526_prime_1536 wolfSSL_DH_1536_prime +#if defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x10100000L +#define DH_set0_pqg wolfSSL_DH_set0_pqg +#endif +#define DH_bits(x) (BN_num_bits(x->p)) +/* for pre 1.1.0 */ +#define get_rfc2409_prime_768 wolfSSL_DH_768_prime +#define get_rfc2409_prime_1024 wolfSSL_DH_1024_prime +#define get_rfc3526_prime_1536 wolfSSL_DH_1536_prime +#define get_rfc3526_prime_2048 wolfSSL_DH_2048_prime +#define get_rfc3526_prime_3072 wolfSSL_DH_3072_prime +#define get_rfc3526_prime_4096 wolfSSL_DH_4096_prime +#define get_rfc3526_prime_6144 wolfSSL_DH_6144_prime +#define get_rfc3526_prime_8192 wolfSSL_DH_8192_prime #ifdef __cplusplus } /* extern "C" */ diff --git a/wolfssl/openssl/ec.h b/wolfssl/openssl/ec.h index ea156db00..baa8f2119 100644 --- a/wolfssl/openssl/ec.h +++ b/wolfssl/openssl/ec.h @@ -132,6 +132,7 @@ WOLFSSL_API WOLFSSL_BIGNUM *wolfSSL_EC_KEY_get0_private_key(const WOLFSSL_EC_KEY *key); WOLFSSL_API WOLFSSL_EC_KEY *wolfSSL_EC_KEY_new_by_curve_name(int nid); +WOLFSSL_API const char* wolfSSL_EC_curve_nid2nist(int nid); WOLFSSL_API WOLFSSL_EC_KEY *wolfSSL_EC_KEY_new(void); WOLFSSL_API @@ -226,6 +227,8 @@ char* wolfSSL_EC_POINT_point2hex(const WOLFSSL_EC_GROUP* group, #define EC_POINT_dump wolfSSL_EC_POINT_dump +#define EC_curve_nid2nist wolfSSL_EC_curve_nid2nist + #ifdef __cplusplus } /* extern "C" */ #endif diff --git a/wolfssl/openssl/evp.h b/wolfssl/openssl/evp.h index d2a65792e..a8320e764 100644 --- a/wolfssl/openssl/evp.h +++ b/wolfssl/openssl/evp.h @@ -243,6 +243,7 @@ struct WOLFSSL_EVP_PKEY_CTX { WOLFSSL_EVP_PKEY *pkey; int op; /* operation */ int padding; + int nbits; }; typedef int WOLFSSL_ENGINE ; @@ -399,10 +400,16 @@ WOLFSSL_API const unsigned char* wolfSSL_EVP_PKEY_get0_hmac(const WOLFSSL_EVP_PK WOLFSSL_API int wolfSSL_EVP_PKEY_sign_init(WOLFSSL_EVP_PKEY_CTX *ctx); WOLFSSL_API int wolfSSL_EVP_PKEY_sign(WOLFSSL_EVP_PKEY_CTX *ctx, unsigned char *sig, size_t *siglen, const unsigned char *tbs, size_t tbslen); +WOLFSSL_API int wolfSSL_EVP_PKEY_keygen_init(WOLFSSL_EVP_PKEY_CTX *ctx); +WOLFSSL_API int wolfSSL_EVP_PKEY_keygen(WOLFSSL_EVP_PKEY_CTX *ctx, + WOLFSSL_EVP_PKEY **ppkey); WOLFSSL_API int wolfSSL_EVP_PKEY_bits(const WOLFSSL_EVP_PKEY *pkey); WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_free(WOLFSSL_EVP_PKEY_CTX *ctx); WOLFSSL_API WOLFSSL_EVP_PKEY_CTX *wolfSSL_EVP_PKEY_CTX_new(WOLFSSL_EVP_PKEY *pkey, WOLFSSL_ENGINE *e); WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_set_rsa_padding(WOLFSSL_EVP_PKEY_CTX *ctx, int padding); +WOLFSSL_API WOLFSSL_EVP_PKEY_CTX *wolfSSL_EVP_PKEY_CTX_new_id(int id, WOLFSSL_ENGINE *e); +WOLFSSL_API int wolfSSL_EVP_PKEY_CTX_set_rsa_keygen_bits(WOLFSSL_EVP_PKEY_CTX *ctx, int bits); + WOLFSSL_API int wolfSSL_EVP_PKEY_decrypt(WOLFSSL_EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen); @@ -420,6 +427,9 @@ WOLFSSL_API int wolfSSL_EVP_PKEY_base_id(const EVP_PKEY *pkey); WOLFSSL_API int wolfSSL_EVP_SignFinal(WOLFSSL_EVP_MD_CTX *ctx, unsigned char *sigret, unsigned int *siglen, WOLFSSL_EVP_PKEY *pkey); WOLFSSL_API int wolfSSL_EVP_SignInit(WOLFSSL_EVP_MD_CTX *ctx, const WOLFSSL_EVP_MD *type); +WOLFSSL_API int wolfSSL_EVP_SignInit_ex(WOLFSSL_EVP_MD_CTX* ctx, + const WOLFSSL_EVP_MD* type, + WOLFSSL_ENGINE *impl); WOLFSSL_API int wolfSSL_EVP_SignUpdate(WOLFSSL_EVP_MD_CTX *ctx, const void *data, size_t len); WOLFSSL_API int wolfSSL_EVP_VerifyFinal(WOLFSSL_EVP_MD_CTX *ctx, unsigned char* sig, unsigned int sig_len, WOLFSSL_EVP_PKEY *pkey); @@ -453,6 +463,7 @@ WOLFSSL_API int wolfSSL_EVP_add_cipher(const WOLFSSL_EVP_CIPHER *cipher); WOLFSSL_API void wolfSSL_EVP_cleanup(void); WOLFSSL_API int wolfSSL_add_all_algorithms(void); WOLFSSL_API int wolfSSL_OpenSSL_add_all_algorithms_noconf(void); +WOLFSSL_API int wolfSSL_EVP_read_pw_string(char*, int, const char*, int); WOLFSSL_API int wolfSSL_PKCS5_PBKDF2_HMAC_SHA1(const char * pass, int passlen, const unsigned char * salt, @@ -605,22 +616,28 @@ typedef WOLFSSL_EVP_CIPHER_CTX EVP_CIPHER_CTX; #define EVP_MD_CTX_copy_ex wolfSSL_EVP_MD_CTX_copy_ex #define EVP_PKEY_sign_init wolfSSL_EVP_PKEY_sign_init #define EVP_PKEY_sign wolfSSL_EVP_PKEY_sign +#define EVP_PKEY_keygen wolfSSL_EVP_PKEY_keygen +#define EVP_PKEY_keygen_init wolfSSL_EVP_PKEY_keygen_init #define EVP_PKEY_bits wolfSSL_EVP_PKEY_bits #define EVP_PKEY_CTX_free wolfSSL_EVP_PKEY_CTX_free #define EVP_PKEY_CTX_new wolfSSL_EVP_PKEY_CTX_new #define EVP_PKEY_CTX_set_rsa_padding wolfSSL_EVP_PKEY_CTX_set_rsa_padding +#define EVP_PKEY_CTX_new_id wolfSSL_EVP_PKEY_CTX_new_id +#define EVP_PKEY_CTX_set_rsa_keygen_bits wolfSSL_EVP_PKEY_CTX_set_rsa_keygen_bits #define EVP_PKEY_decrypt wolfSSL_EVP_PKEY_decrypt #define EVP_PKEY_decrypt_init wolfSSL_EVP_PKEY_decrypt_init #define EVP_PKEY_encrypt wolfSSL_EVP_PKEY_encrypt #define EVP_PKEY_encrypt_init wolfSSL_EVP_PKEY_encrypt_init #define EVP_PKEY_new wolfSSL_PKEY_new #define EVP_PKEY_free wolfSSL_EVP_PKEY_free +#define EVP_PKEY_up_ref wolfSSL_EVP_PKEY_up_ref #define EVP_PKEY_size wolfSSL_EVP_PKEY_size #define EVP_PKEY_type wolfSSL_EVP_PKEY_type #define EVP_PKEY_base_id wolfSSL_EVP_PKEY_base_id #define EVP_PKEY_id wolfSSL_EVP_PKEY_id #define EVP_SignFinal wolfSSL_EVP_SignFinal #define EVP_SignInit wolfSSL_EVP_SignInit +#define EVP_SignInit_ex wolfSSL_EVP_SignInit_ex #define EVP_SignUpdate wolfSSL_EVP_SignUpdate #define EVP_VerifyFinal wolfSSL_EVP_VerifyFinal #define EVP_VerifyInit wolfSSL_EVP_VerifyInit @@ -637,6 +654,7 @@ typedef WOLFSSL_EVP_CIPHER_CTX EVP_CIPHER_CTX; #define EVP_add_digest wolfSSL_EVP_add_digest #define EVP_add_cipher wolfSSL_EVP_add_cipher #define EVP_cleanup wolfSSL_EVP_cleanup +#define EVP_read_pw_string wolfSSL_EVP_read_pw_string #define OpenSSL_add_all_digests() wolfCrypt_Init() #define OpenSSL_add_all_ciphers() wolfCrypt_Init() @@ -669,6 +687,10 @@ typedef WOLFSSL_EVP_CIPHER_CTX EVP_CIPHER_CTX; /* They define this as 32. Using the same value here. */ #endif +#ifndef EVP_MAX_IV_LENGTH + #define EVP_MAX_IV_LENGTH 16 +#endif + WOLFSSL_API void printPKEY(WOLFSSL_EVP_PKEY *k); #ifdef __cplusplus diff --git a/wolfssl/openssl/include.am b/wolfssl/openssl/include.am index ecba7f04d..775e60dc5 100644 --- a/wolfssl/openssl/include.am +++ b/wolfssl/openssl/include.am @@ -41,5 +41,6 @@ nobase_include_HEADERS+= \ wolfssl/openssl/stack.h \ wolfssl/openssl/ui.h \ wolfssl/openssl/x509.h \ + wolfssl/openssl/x509_vfy.h \ wolfssl/openssl/x509v3.h \ wolfssl/openssl/rc4.h diff --git a/wolfssl/openssl/objects.h b/wolfssl/openssl/objects.h index 9fc4a32db..01b106746 100644 --- a/wolfssl/openssl/objects.h +++ b/wolfssl/openssl/objects.h @@ -39,11 +39,21 @@ #define OBJ_sn2nid wolfSSL_OBJ_sn2nid #define OBJ_nid2ln wolfSSL_OBJ_nid2ln #define OBJ_txt2nid wolfSSL_OBJ_txt2nid +#define OBJ_txt2obj wolfSSL_OBJ_txt2obj #define OBJ_nid2obj wolfSSL_OBJ_nid2obj #define OBJ_obj2txt wolfSSL_OBJ_obj2txt #define OBJ_cleanup wolfSSL_OBJ_cleanup +#define OBJ_cmp wolfSSL_OBJ_cmp +#define OBJ_create wolfSSL_OBJ_create #define ASN1_OBJECT_free wolfSSL_ASN1_OBJECT_free +/* not required for wolfSSL */ +#define OPENSSL_load_builtin_modules() + + +#define NID_ad_OCSP 178 +#define NID_ad_ca_issuers 179 + #ifdef __cplusplus } /* extern "C" */ diff --git a/wolfssl/openssl/ocsp.h b/wolfssl/openssl/ocsp.h index 31fb6c98e..0a0f27d85 100644 --- a/wolfssl/openssl/ocsp.h +++ b/wolfssl/openssl/ocsp.h @@ -33,8 +33,15 @@ #define OCSP_CERTID WOLFSSL_OCSP_CERTID #define OCSP_ONEREQ WOLFSSL_OCSP_ONEREQ +#define OCSP_REVOKED_STATUS_NOSTATUS -1 + + #define OCSP_RESPONSE_STATUS_SUCCESSFUL 0 +#define OCSP_RESPONSE_STATUS_TRYLATER 3 + #define V_OCSP_CERTSTATUS_GOOD 0 +#define V_OCSP_CERTSTATUS_REVOKED 1 +#define V_OCSP_CERTSTATUS_UNKNOWN 2 #define OCSP_resp_find_status wolfSSL_OCSP_resp_find_status #define OCSP_cert_status_str wolfSSL_OCSP_cert_status_str @@ -53,11 +60,21 @@ #define OCSP_response_status wolfSSL_OCSP_response_status #define OCSP_response_status_str wolfSSL_OCSP_response_status_str #define OCSP_response_get1_basic wolfSSL_OCSP_response_get1_basic +#define OCSP_response_create wolfSSL_OCSP_response_create #define OCSP_REQUEST_new wolfSSL_OCSP_REQUEST_new #define OCSP_REQUEST_free wolfSSL_OCSP_REQUEST_free #define i2d_OCSP_REQUEST wolfSSL_i2d_OCSP_REQUEST #define OCSP_request_add0_id wolfSSL_OCSP_request_add0_id +#define OCSP_request_add1_nonce wolfSSL_OCSP_request_add1_nonce +#define OCSP_check_nonce wolfSSL_OCSP_check_nonce +#define OCSP_id_get0_info wolfSSL_OCSP_id_get0_info +#define OCSP_crl_reason_str wolfSSL_OCSP_crl_reason_str +#define OCSP_REQUEST_add_ext wolfSSL_OCSP_REQUEST_add_ext + +#define OCSP_CERTID_dup wolfSSL_OCSP_CERTID_dup + +#define i2d_OCSP_REQUEST_bio wolfSSL_i2d_OCSP_REQUEST_bio #endif /* HAVE_OCSP */ diff --git a/wolfssl/openssl/opensslv.h b/wolfssl/openssl/opensslv.h index a2334b621..4bc495eea 100644 --- a/wolfssl/openssl/opensslv.h +++ b/wolfssl/openssl/opensslv.h @@ -26,7 +26,10 @@ /* api version compatibility */ -#if defined(OPENSSL_ALL) || defined(HAVE_STUNNEL) || defined(HAVE_LIGHTY) || \ +#if defined(WOLFSSL_APACHE_HTTPD) + /* For Apache httpd, Use 1.1.0 compatibility */ + #define OPENSSL_VERSION_NUMBER 0x10100000L +#elif defined(OPENSSL_ALL) || defined(HAVE_STUNNEL) || defined(HAVE_LIGHTY) || \ defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) /* version number can be increased for Lighty after compatibility for ECDH is added */ @@ -36,6 +39,6 @@ #endif #define OPENSSL_VERSION_TEXT LIBWOLFSSL_VERSION_STRING - +#define OPENSSL_VERSION 0 #endif /* header */ diff --git a/wolfssl/openssl/pem.h b/wolfssl/openssl/pem.h index 6bf85e81b..3434853ed 100644 --- a/wolfssl/openssl/pem.h +++ b/wolfssl/openssl/pem.h @@ -51,6 +51,11 @@ WOLFSSL_RSA* wolfSSL_PEM_read_bio_RSAPrivateKey(WOLFSSL_BIO* bio, pem_password_cb* cb, void* arg); WOLFSSL_API +WOLFSSL_EC_GROUP* wolfSSL_PEM_read_bio_ECPKParameters(WOLFSSL_BIO* bio, + WOLFSSL_EC_GROUP** group, + pem_password_cb* cb, + void* pass); +WOLFSSL_API int wolfSSL_PEM_write_mem_RSAPrivateKey(RSA* rsa, const EVP_CIPHER* cipher, unsigned char* passwd, int len, unsigned char **pem, int *plen); @@ -179,6 +184,7 @@ int wolfSSL_PEM_write_DHparams(XFILE fp, WOLFSSL_DH* dh); /* RSA */ #define PEM_write_bio_RSAPrivateKey wolfSSL_PEM_write_bio_RSAPrivateKey #define PEM_read_bio_RSAPrivateKey wolfSSL_PEM_read_bio_RSAPrivateKey +#define PEM_read_bio_ECPKParameters wolfSSL_PEM_read_bio_ECPKParameters #define PEM_write_RSAPrivateKey wolfSSL_PEM_write_RSAPrivateKey #define PEM_write_RSA_PUBKEY wolfSSL_PEM_write_RSA_PUBKEY #define PEM_write_RSAPublicKey wolfSSL_PEM_write_RSAPublicKey diff --git a/wolfssl/openssl/rsa.h b/wolfssl/openssl/rsa.h index 3e2007a56..d1a4bed3c 100644 --- a/wolfssl/openssl/rsa.h +++ b/wolfssl/openssl/rsa.h @@ -95,6 +95,9 @@ WOLFSSL_API int wolfSSL_RSA_GenAdd(WOLFSSL_RSA*); WOLFSSL_API int wolfSSL_RSA_LoadDer(WOLFSSL_RSA*, const unsigned char*, int sz); WOLFSSL_API int wolfSSL_RSA_LoadDer_ex(WOLFSSL_RSA*, const unsigned char*, int sz, int opt); +WOLFSSL_API void wolfSSL_RSA_get0_key(const WOLFSSL_RSA *r, + const WOLFSSL_BIGNUM **n, const WOLFSSL_BIGNUM **e, const WOLFSSL_BIGNUM **d); + #define WOLFSSL_RSA_LOAD_PRIVATE 1 #define WOLFSSL_RSA_LOAD_PUBLIC 2 #define WOLFSSL_RSA_F4 0x10001L @@ -111,9 +114,11 @@ WOLFSSL_API int wolfSSL_RSA_LoadDer_ex(WOLFSSL_RSA*, const unsigned char*, int s #define RSA_size wolfSSL_RSA_size #define RSA_sign wolfSSL_RSA_sign -#define RSA_verify wolfSSL_RSA_verify +#define RSA_verify wolfSSL_RSA_verify #define RSA_public_decrypt wolfSSL_RSA_public_decrypt +#define RSA_get0_key wolfSSL_RSA_get0_key + #define RSA_F4 WOLFSSL_RSA_F4 #ifdef __cplusplus diff --git a/wolfssl/openssl/ssl.h b/wolfssl/openssl/ssl.h index b1f239ba2..39e898fe7 100644 --- a/wolfssl/openssl/ssl.h +++ b/wolfssl/openssl/ssl.h @@ -66,6 +66,7 @@ typedef WOLFSSL_CTX SSL_CTX; typedef WOLFSSL_X509 X509; typedef WOLFSSL_X509 X509_REQ; typedef WOLFSSL_X509_NAME X509_NAME; +typedef WOLFSSL_X509_INFO X509_INFO; typedef WOLFSSL_X509_CHAIN X509_CHAIN; typedef WOLFSSL_STACK EXTENDED_KEY_USAGE; @@ -81,19 +82,23 @@ typedef WOLFSSL_X509_LOOKUP X509_LOOKUP; typedef WOLFSSL_X509_LOOKUP_METHOD X509_LOOKUP_METHOD; typedef WOLFSSL_X509_CRL X509_CRL; typedef WOLFSSL_X509_EXTENSION X509_EXTENSION; +typedef WOLFSSL_X509_PUBKEY X509_PUBKEY; +typedef WOLFSSL_X509_ALGOR X509_ALGOR; typedef WOLFSSL_ASN1_TIME ASN1_TIME; typedef WOLFSSL_ASN1_INTEGER ASN1_INTEGER; typedef WOLFSSL_ASN1_OBJECT ASN1_OBJECT; typedef WOLFSSL_ASN1_STRING ASN1_STRING; +typedef WOLFSSL_ASN1_TYPE ASN1_TYPE; typedef WOLFSSL_dynlock_value CRYPTO_dynlock_value; typedef WOLFSSL_BUF_MEM BUF_MEM; -typedef WOLFSSL_GENERAL_NAME GENERAL_NAME; typedef WOLFSSL_GENERAL_NAMES GENERAL_NAMES; +typedef WOLFSSL_GENERAL_NAME GENERAL_NAME; #define ASN1_UTCTIME WOLFSSL_ASN1_TIME #define ASN1_GENERALIZEDTIME WOLFSSL_ASN1_TIME typedef WOLFSSL_COMP_METHOD COMP_METHOD; +typedef WOLFSSL_COMP SSL_COMP; typedef WOLFSSL_X509_REVOKED X509_REVOKED; typedef WOLFSSL_X509_OBJECT X509_OBJECT; typedef WOLFSSL_X509_STORE X509_STORE; @@ -113,6 +118,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; /* depreciated */ #define CRYPTO_thread_id wolfSSL_thread_id #define CRYPTO_set_id_callback wolfSSL_set_id_callback + #define CRYPTO_LOCK 0x01 #define CRYPTO_UNLOCK 0x02 #define CRYPTO_READ 0x04 @@ -128,7 +134,8 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define CRYPTO_cleanup_all_ex_data wolfSSL_cleanup_all_ex_data /* this function was used to set the default malloc, free, and realloc */ -#define CRYPTO_malloc_init() /* CRYPTO_malloc_init is not needed */ +#define CRYPTO_malloc_init() 0 /* CRYPTO_malloc_init is not needed */ +#define OPENSSL_malloc_init() 0 /* OPENSSL_malloc_init is not needed */ #define SSL_get_client_random(ssl,out,outSz) \ wolfSSL_get_client_random((ssl),(out),(outSz)) @@ -155,6 +162,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define d2i_PUBKEY_bio wolfSSL_d2i_PUBKEY_bio #define d2i_PrivateKey wolfSSL_d2i_PrivateKey #define d2i_AutoPrivateKey wolfSSL_d2i_AutoPrivateKey +#define i2d_PrivateKey wolfSSL_i2d_PrivateKey #define SSL_use_PrivateKey wolfSSL_use_PrivateKey #define SSL_use_PrivateKey_ASN1 wolfSSL_use_PrivateKey_ASN1 #define SSL_use_RSAPrivateKey_ASN1 wolfSSL_use_RSAPrivateKey_ASN1 @@ -167,6 +175,8 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define SSLv2_server_method wolfSSLv2_server_method #define SSLv3_server_method wolfSSLv3_server_method #define SSLv3_client_method wolfSSLv3_client_method +#define TLS_client_method wolfTLS_client_method +#define TLS_server_method wolfTLS_server_method #define TLSv1_method wolfTLSv1_method #define TLSv1_server_method wolfTLSv1_server_method #define TLSv1_client_method wolfTLSv1_client_method @@ -182,6 +192,8 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define X509_FILETYPE_ASN1 SSL_FILETYPE_ASN1 +#define X509_F_X509_CHECK_PRIVATE_KEY 128 + #ifdef WOLFSSL_DTLS #define DTLSv1_client_method wolfDTLSv1_client_method #define DTLSv1_server_method wolfDTLSv1_server_method @@ -218,6 +230,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define SSL_CTX_free wolfSSL_CTX_free #define SSL_free wolfSSL_free #define SSL_shutdown wolfSSL_shutdown +#define SSL_set_timeout wolfSSL_set_timeout #define SSL_CTX_set_quiet_shutdown wolfSSL_CTX_set_quiet_shutdown #define SSL_set_quiet_shutdown wolfSSL_set_quiet_shutdown @@ -230,6 +243,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define SSL_CTX_set_verify wolfSSL_CTX_set_verify #define SSL_set_verify wolfSSL_set_verify +#define SSL_set_verify_result wolfSSL_set_verify_result #define SSL_pending wolfSSL_pending #define SSL_load_error_strings wolfSSL_load_error_strings #define SSL_library_init wolfSSL_library_init @@ -248,6 +262,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define SSL_session_reused wolfSSL_session_reused #define SSL_SESSION_free wolfSSL_SESSION_free #define SSL_is_init_finished wolfSSL_is_init_finished + #define SSL_get_version wolfSSL_get_version #define SSL_get_current_cipher wolfSSL_get_current_cipher @@ -255,6 +270,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define SSL_get_cipher wolfSSL_get_cipher_name #define SSL_CIPHER_description wolfSSL_CIPHER_description #define SSL_CIPHER_get_name wolfSSL_CIPHER_get_name +#define SSL_CIPHER_get_version wolfSSL_CIPHER_get_version #define SSL_get1_session wolfSSL_get1_session #define SSL_get_keyblock_size wolfSSL_get_keyblock_size @@ -266,7 +282,6 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define ASN1_BOOLEAN WOLFSSL_ASN1_BOOLEAN #define X509_get_ext wolfSSL_X509_get_ext #define X509_cmp wolfSSL_X509_cmp - #define X509_get_ext_count wolfSSL_X509_get_ext_count #define X509_EXTENSION_get_object wolfSSL_X509_EXTENSION_get_object #define X509_EXTENSION_get_critical wolfSSL_X509_EXTENSION_get_critical #define X509_EXTENSION_get_data wolfSSL_X509_EXTENSION_get_data @@ -284,28 +299,36 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define PEM_read_bio_X509 wolfSSL_PEM_read_bio_X509 #define PEM_read_bio_X509_AUX wolfSSL_PEM_read_bio_X509_AUX #define PEM_read_X509 wolfSSL_PEM_read_X509 +#define PEM_X509_INFO_read_bio wolfSSL_PEM_X509_INFO_read_bio #define PEM_write_bio_X509 wolfSSL_PEM_write_bio_X509 #define PEM_write_bio_X509_AUX wolfSSL_PEM_write_bio_X509_AUX +#define i2d_PrivateKey wolfSSL_i2d_PrivateKey #define i2d_X509_REQ wolfSSL_i2d_X509_REQ #define X509_REQ_new wolfSSL_X509_REQ_new #define X509_REQ_free wolfSSL_X509_REQ_free #define X509_REQ_sign wolfSSL_X509_REQ_sign +#define X509_REQ_add_extensions wolfSSL_X509_REQ_add_extensions #define X509_REQ_set_subject_name wolfSSL_X509_REQ_set_subject_name #define X509_REQ_set_pubkey wolfSSL_X509_REQ_set_pubkey #define PEM_write_bio_X509_REQ wolfSSL_PEM_write_bio_X509_REQ #define X509_new wolfSSL_X509_new +#define X509_up_ref wolfSSL_X509_up_ref #define X509_free wolfSSL_X509_free #define X509_load_certificate_file wolfSSL_X509_load_certificate_file #define X509_digest wolfSSL_X509_digest +#define X509_get_ext_count wolfSSL_X509_get_ext_count #define X509_get_ext_d2i wolfSSL_X509_get_ext_d2i #define X509_get_ext_by_NID wolfSSL_X509_get_ext_by_NID +#define X509_get_ext wolfSSL_X509_get_ext +#define X509_get_ext_by_NID wolfSSL_X509_get_ext_by_NID +#define X509_add_ext wolfSSL_X509_add_ext #define X509_get_issuer_name wolfSSL_X509_get_issuer_name #define X509_get_subject_name wolfSSL_X509_get_subject_name #define X509_get_pubkey wolfSSL_X509_get_pubkey -#define X509_get_notBefore(cert) (ASN1_TIME*)wolfSSL_X509_notBefore((cert)) -#define X509_get_notAfter(cert) (ASN1_TIME*)wolfSSL_X509_notAfter((cert)) +#define X509_get_notBefore wolfSSL_X509_get_notBefore +#define X509_get_notAfter wolfSSL_X509_get_notAfter #define X509_get_serialNumber wolfSSL_X509_get_serialNumber #define X509_get0_pubkey_bitstr wolfSSL_X509_get0_pubkey_bitstr #define X509_get_ex_new_index wolfSSL_X509_get_ex_new_index @@ -317,7 +340,13 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #endif #define X509_get_signature_nid wolfSSL_X509_get_signature_nid #define X509_set_subject_name wolfSSL_X509_set_subject_name +#define X509_set_issuer_name wolfSSL_X509_set_issuer_name #define X509_set_pubkey wolfSSL_X509_set_pubkey +#define X509_set_notAfter wolfSSL_X509_set_notAfter +#define X509_set_notBefore wolfSSL_X509_set_notBefore +#define X509_set_serialNumber wolfSSL_X509_set_serialNumber +#define X509_set_version wolfSSL_X509_set_version +#define X509_sign wolfSSL_X509_sign #define X509_print wolfSSL_X509_print #define X509_verify_cert_error_string wolfSSL_X509_verify_cert_error_string #define X509_verify_cert wolfSSL_X509_verify_cert @@ -328,18 +357,42 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define X509_check_issued wolfSSL_X509_check_issued #define X509_dup wolfSSL_X509_dup +#define X509_EXTENSION_get_object wolfSSL_X509_EXTENSION_get_object +#define X509_EXTENSION_get_data wolfSSL_X509_EXTENSION_get_data + #define sk_X509_new wolfSSL_sk_X509_new +#define sk_X509_new_null wolfSSL_sk_X509_new #define sk_X509_num wolfSSL_sk_X509_num #define sk_X509_value wolfSSL_sk_X509_value +#define sk_X509_shift wolfSSL_sk_X509_shift #define sk_X509_push wolfSSL_sk_X509_push #define sk_X509_pop wolfSSL_sk_X509_pop #define sk_X509_pop_free wolfSSL_sk_X509_pop_free #define sk_X509_dup wolfSSL_sk_X509_dup #define sk_X509_free wolfSSL_sk_X509_free +#define sk_X509_EXTENSION_num wolfSSL_sk_X509_EXTENSION_num +#define sk_X509_EXTENSION_value wolfSSL_sk_X509_EXTENSION_value +#define sk_X509_EXTENSION_new_null wolfSSL_sk_X509_EXTENSION_new_null +#define sk_X509_EXTENSION_pop_free wolfSSL_sk_X509_EXTENSION_pop_free +#define sk_X509_EXTENSION_push wolfSSL_sk_X509_EXTENSION_push +#define X509_EXTENSION_free wolfSSL_X509_EXTENSION_free + +#define X509_INFO_new wolfSSL_X509_INFO_new +#define X509_INFO_free wolfSSL_X509_INFO_free + +#define sk_X509_INFO_new_null wolfSSL_sk_X509_INFO_new_null +#define sk_X509_INFO_num wolfSSL_sk_X509_INFO_num +#define sk_X509_INFO_value wolfSSL_sk_X509_INFO_value +#define sk_X509_INFO_push wolfSSL_sk_X509_INFO_push +#define sk_X509_INFO_pop wolfSSL_sk_X509_INFO_pop +#define sk_X509_INFO_pop_free wolfSSL_sk_X509_INFO_pop_free +#define sk_X509_INFO_free wolfSSL_sk_X509_INFO_free + #define i2d_X509_NAME wolfSSL_i2d_X509_NAME #define X509_NAME_new wolfSSL_X509_NAME_new #define X509_NAME_free wolfSSL_X509_NAME_free +#define X509_NAME_dup wolfSSL_X509_NAME_dup #define X509_NAME_get_text_by_NID wolfSSL_X509_NAME_get_text_by_NID #define X509_NAME_cmp wolfSSL_X509_NAME_cmp #define X509_NAME_ENTRY_free wolfSSL_X509_NAME_ENTRY_free @@ -353,11 +406,20 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define X509_cmp_current_time wolfSSL_X509_cmp_current_time #define X509_cmp_time wolfSSL_X509_cmp_time -#define sk_X509_NAME_pop_free wolfSSL_sk_X509_NAME_pop_free +#define sk_ACCESS_DESCRIPTION_num wolfSSL_sk_ACCESS_DESCRIPTION_num +#define sk_ACCESS_DESCRIPTION_value wolfSSL_sk_ACCESS_DESCRIPTION_value + +#define sk_X509_NAME_new wolfSSL_sk_X509_NAME_new +#define sk_X509_NAME_push wolfSSL_sk_X509_NAME_push +#define sk_X509_NAME_find wolfSSL_sk_X509_NAME_find +#define sk_X509_NAME_set_cmp_func wolfSSL_sk_X509_NAME_set_cmp_func #define sk_X509_NAME_num wolfSSL_sk_X509_NAME_num #define sk_X509_NAME_value wolfSSL_sk_X509_NAME_value +#define sk_X509_NAME_pop wolfSSL_sk_X509_NAME_pop +#define sk_X509_NAME_pop_free wolfSSL_sk_X509_NAME_pop_free +#define sk_X509_NAME_free wolfSSL_sk_X509_NAME_free - typedef WOLFSSL_X509_NAME_ENTRY X509_NAME_ENTRY; +typedef WOLFSSL_X509_NAME_ENTRY X509_NAME_ENTRY; #define X509_NAME_entry_count wolfSSL_X509_NAME_entry_count #define X509_NAME_ENTRY_get_object wolfSSL_X509_NAME_ENTRY_get_object @@ -384,6 +446,12 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define X509_STORE_CTX_cleanup wolfSSL_X509_STORE_CTX_cleanup #define X509_STORE_CTX_set_error wolfSSL_X509_STORE_CTX_set_error #define X509_STORE_CTX_get_ex_data wolfSSL_X509_STORE_CTX_get_ex_data +#define X509_STORE_CTX_set_ex_data wolfSSL_X509_STORE_CTX_set_ex_data +#define X509_STORE_CTX_set_depth wolfSSL_X509_STORE_CTX_set_depth +#define X509_STORE_CTX_get0_current_issuer \ + wolfSSL_X509_STORE_CTX_get0_current_issuer +#define X509_STORE_CTX_get0_store wolfSSL_X509_STORE_CTX_get0_store + #define X509_STORE_new wolfSSL_X509_STORE_new #define X509_STORE_free wolfSSL_X509_STORE_free #define X509_STORE_add_lookup wolfSSL_X509_STORE_add_lookup @@ -397,6 +465,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define X509_VERIFY_PARAM_set_hostflags wolfSSL_X509_VERIFY_PARAM_set_hostflags #define X509_VERIFY_PARAM_set1_host wolfSSL_X509_VERIFY_PARAM_set1_host #define X509_VERIFY_PARAM_set1_ip_asc wolfSSL_X509_VERIFY_PARAM_set1_ip_asc +#define X509_STORE_load_locations wolfSSL_X509_STORE_load_locations #define X509_LOOKUP_add_dir wolfSSL_X509_LOOKUP_add_dir #define X509_LOOKUP_load_file wolfSSL_X509_LOOKUP_load_file @@ -413,6 +482,11 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define X509_CRL_verify wolfSSL_X509_CRL_verify #define X509_CRL_get_REVOKED wolfSSL_X509_CRL_get_REVOKED +#define X509_get_X509_PUBKEY wolfSSL_X509_get_X509_PUBKEY +#define X509_get0_tbs_sigalg wolfSSL_X509_get0_tbs_sigalg +#define X509_PUBKEY_get0_param wolfSSL_X509_PUBKEY_get0_param +#define X509_ALGOR_get0 wolfSSL_X509_ALGOR_get0 + #define sk_X509_REVOKED_num wolfSSL_sk_X509_REVOKED_num #define sk_X509_REVOKED_value wolfSSL_sk_X509_REVOKED_value @@ -427,6 +501,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define BIO_new wolfSSL_BIO_new #define BIO_free wolfSSL_BIO_free +#define BIO_vfree wolfSSL_BIO_vfree #define BIO_free_all wolfSSL_BIO_free_all #define BIO_nread0 wolfSSL_BIO_nread0 #define BIO_nread wolfSSL_BIO_nread @@ -453,6 +528,7 @@ typedef WOLFSSL_X509_VERIFY_PARAM X509_VERIFY_PARAM; #define BIO_s_mem wolfSSL_BIO_s_mem #define BIO_f_base64 wolfSSL_BIO_f_base64 #define BIO_set_flags wolfSSL_BIO_set_flags +#define BIO_set_nbio wolfSSL_BIO_set_nbio #define SSLeay_add_ssl_algorithms wolfSSL_add_all_algorithms #define SSLeay_add_all_algorithms wolfSSL_add_all_algorithms @@ -504,19 +580,23 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define ASN1_STRING_to_UTF8 wolfSSL_ASN1_STRING_to_UTF8 #define ASN1_STRING_print_ex wolfSSL_ASN1_STRING_print_ex #define ASN1_STRING_print(x, y) wolfSSL_ASN1_STRING_print ((WOLFSSL_BIO*)(x), (WOLFSSL_ASN1_STRING*)(y)) +#define d2i_DISPLAYTEXT wolfSSL_d2i_DISPLAYTEXT #define ASN1_UTCTIME_pr wolfSSL_ASN1_UTCTIME_pr #define ASN1_IA5STRING WOLFSSL_ASN1_STRING #define ASN1_OCTET_STRING WOLFSSL_ASN1_STRING +#define ASN1_BOOLEAN WOLFSSL_ASN1_BOOLEAN #define SSL_load_client_CA_file wolfSSL_load_client_CA_file #define SSL_CTX_get_client_CA_list wolfSSL_SSL_CTX_get_client_CA_list #define SSL_CTX_set_client_CA_list wolfSSL_CTX_set_client_CA_list +#define SSL_CTX_set_client_cert_cb wolfSSL_CTX_set_client_cert_cb #define SSL_CTX_set_cert_store wolfSSL_CTX_set_cert_store #define SSL_CTX_get_cert_store(x) wolfSSL_CTX_get_cert_store ((WOLFSSL_CTX*) (x)) +#define SSL_get_client_CA_list wolfSSL_get_client_CA_list #define SSL_get_ex_data_X509_STORE_CTX_idx wolfSSL_get_ex_data_X509_STORE_CTX_idx #define SSL_get_ex_data wolfSSL_get_ex_data @@ -598,6 +678,7 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define ERR_get_error_line_data wolfSSL_ERR_get_error_line_data #define ERR_get_error wolfSSL_ERR_get_error #define ERR_print_errors_fp(file) wolfSSL_ERR_dump_errors_fp((file)) +#define ERR_print_errors wolfSSL_ERR_print_errors #define ERR_clear_error wolfSSL_ERR_clear_error #define ERR_free_strings wolfSSL_ERR_free_strings #define ERR_remove_state wolfSSL_ERR_remove_state @@ -607,6 +688,9 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define ERR_reason_error_string wolfSSL_ERR_reason_error_string #define ERR_load_BIO_strings wolfSSL_ERR_load_BIO_strings +#define PEMerr(func, reason) wolfSSL_ERR_put_error(ERR_LIB_PEM,\ + (func), (reason), __FILE__, __LINE__) + #define SSLv23_server_method wolfSSLv23_server_method #define SSL_CTX_set_options wolfSSL_CTX_set_options #define SSL_CTX_get_options wolfSSL_CTX_get_options @@ -655,6 +739,7 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define SSL_SESSION_set_timeout wolfSSL_SSL_SESSION_set_timeout #define SSL_SESSION_get_timeout wolfSSL_SESSION_get_timeout #define SSL_SESSION_get_time wolfSSL_SESSION_get_time + #define SSL_CTX_get_ex_new_index wolfSSL_CTX_get_ex_new_index #define PEM_read wolfSSL_PEM_read #define PEM_write wolfSSL_PEM_write @@ -693,7 +778,8 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; enum { GEN_DNS = 0x02, /* ASN_DNS_TYPE */ GEN_EMAIL = 0x01, /* ASN_RFC822_TYPE */ - GEN_URI = 0x06 /* ASN_URI_TYPE */ + GEN_URI = 0x06, /* ASN_URI_TYPE */ + GEN_RID = 0x08, /* Registered ID, not supported */ }; #define PEM_read_bio_DHparams wolfSSL_PEM_read_bio_DHparams @@ -711,6 +797,9 @@ enum { #define sk_SSL_COMP_zero wolfSSL_sk_SSL_COMP_zero #define sk_SSL_CIPHER_value wolfSSL_sk_SSL_CIPHER_value #endif /* OPENSSL_ALL || WOLFSSL_HAPROXY */ +#define sk_SSL_CIPHER_dup wolfSSL_sk_SSL_CIPHER_dup +#define sk_SSL_CIPHER_free wolfSSL_sk_SSL_CIPHER_free +#define sk_SSL_CIPHER_find wolfSSL_sk_SSL_CIPHER_find #if defined(OPENSSL_ALL) || defined(WOLFSSL_ASIO) #include @@ -722,8 +811,11 @@ enum { #define SSL_R_SHORT_READ 10 #define ERR_R_PEM_LIB 9 #define V_ASN1_IA5STRING 22 +#define V_ASN1_UTF8STRING 12 #define SSL_CTRL_MODE 33 +#define SSL_CTRL_CLEAR_EXTRA_CHAIN_CERTS 83 + #define SSL_CTX_clear_chain_certs(ctx) SSL_CTX_set0_chain(ctx,NULL) #define d2i_RSAPrivateKey_bio wolfSSL_d2i_RSAPrivateKey_bio #define SSL_CTX_use_RSAPrivateKey wolfSSL_CTX_use_RSAPrivateKey @@ -743,7 +835,9 @@ enum { #define SSL_CTX_set_tmp_dh wolfSSL_CTX_set_tmp_dh +#define BIO_new_fp wolfSSL_BIO_new_fp #define BIO_new_file wolfSSL_BIO_new_file +#define BIO_new_fp wolfSSL_BIO_new_fp #define BIO_ctrl wolfSSL_BIO_ctrl #define BIO_ctrl_pending wolfSSL_BIO_ctrl_pending #define BIO_wpending wolfSSL_BIO_wpending @@ -773,6 +867,9 @@ enum { #define SSL_set_tmp_dh wolfSSL_set_tmp_dh #define SSL_clear_num_renegotiations wolfSSL_clear_num_renegotiations #define SSL_total_renegotiations wolfSSL_total_renegotiations +#define SSL_num_renegotiations wolfSSL_num_renegotiations +#define SSL_renegotiate wolfSSL_Rehandshake +#define SSL_get_secure_renegotiation_support wolfSSL_SSL_get_secure_renegotiation_support #define SSL_set_tlsext_debug_arg wolfSSL_set_tlsext_debug_arg #define SSL_set_tlsext_status_type wolfSSL_set_tlsext_status_type #define SSL_set_tlsext_status_exts wolfSSL_set_tlsext_status_exts @@ -790,6 +887,10 @@ enum { #define SSL_CTX_set_tlsext_opaque_prf_input_callback_arg \ wolfSSL_CTX_set_tlsext_opaque_prf_input_callback_arg #define SSL_get_server_random wolfSSL_get_server_random +#define SSL_get_server_tmp_key wolfSSL_get_server_tmp_key + +#define SSL_CTX_set_min_proto_version wolfSSL_CTX_set_min_proto_version +#define SSL_CTX_set_max_proto_version wolfSSL_CTX_set_max_proto_version #define SSL_get_tlsext_status_exts wolfSSL_get_tlsext_status_exts @@ -842,7 +943,11 @@ enum { #define SSL2_VERSION 0x0002 #define SSL3_VERSION 0x0300 #define TLS1_VERSION 0x0301 +#define TLS1_1_VERSION 0x0302 +#define TLS1_2_VERSION 0x0303 +#define TLS1_3_VERSION 0x0304 #define DTLS1_VERSION 0xFEFF +#define DTLS1_2_VERSION 0xFEFD #define SSL23_ST_SR_CLNT_HELLO_A (0x210|0x2000) #define SSL3_ST_SR_CLNT_HELLO_A (0x110|0x2000) #define ASN1_STRFLGS_ESC_MSB 4 @@ -861,15 +966,23 @@ enum { #define SSL_get_state wolfSSL_get_state #define SSL_state_string_long wolfSSL_state_string_long +#define GENERAL_NAME_new wolfSSL_GENERAL_NAME_new +#define GENERAL_NAME_free wolfSSL_GENERAL_NAME_free +#define sk_GENERAL_NAME_push wolfSSL_sk_GENERAL_NAME_push #define sk_GENERAL_NAME_value wolfSSL_sk_GENERAL_NAME_value #define SSL_SESSION_get_ex_data wolfSSL_SESSION_get_ex_data #define SSL_SESSION_set_ex_data wolfSSL_SESSION_set_ex_data #define SSL_SESSION_get_ex_new_index wolfSSL_SESSION_get_ex_new_index #define SSL_SESSION_get_id wolfSSL_SESSION_get_id +#define SSL_SESSION_print wolfSSL_SESSION_print #define sk_GENERAL_NAME_pop_free wolfSSL_sk_GENERAL_NAME_pop_free #define GENERAL_NAME_free wolfSSL_GENERAL_NAME_free #define GENERAL_NAMES_free wolfSSL_GENERAL_NAMES_free +#define AUTHORITY_INFO_ACCESS_free wolfSSL_AUTHORITY_INFO_ACCESS_free +#define sk_ACCESS_DESCRIPTION_pop_free wolfSSL_sk_ACCESS_DESCRIPTION_pop_free +#define ACCESS_DESCRIPTION_free NULL + #define SSL3_AL_FATAL 2 #define SSL_TLSEXT_ERR_OK 0 #define SSL_TLSEXT_ERR_ALERT_FATAL alert_fatal @@ -897,13 +1010,20 @@ enum { #define SSL_CTX_set_msg_callback_arg wolfSSL_CTX_set_msg_callback_arg #define SSL_set_msg_callback_arg wolfSSL_set_msg_callback_arg +#define SSL_CTX_clear_extra_chain_certs wolfSSL_CTX_clear_extra_chain_certs + /* Nginx uses this to determine if reached end of certs in file. * PEM_read_bio_X509 is called and the return error is lost. * The error that needs to be detected is: SSL_NO_PEM_HEADER. */ -#define ERR_GET_LIB(l) (int)((((unsigned long)l)>>24L)&0xffL) +#define ERR_GET_LIB(l) (int)((((unsigned long)l) >> 24L) & 0xffL) +#define ERR_GET_FUNC(l) (int)((((unsigned long)l) >> 12L) & 0xfffL) + +#define PEM_F_PEM_DEF_CALLBACK 100 + #define PEM_R_NO_START_LINE 108 +#define PEM_R_PROBLEMS_GETTING_PASSWORD 109 #define ERR_LIB_PEM 9 #define ERR_LIB_X509 10 @@ -957,6 +1077,7 @@ enum { #define SSL_get_wbio wolfSSL_SSL_get_wbio #define SSL_do_handshake wolfSSL_SSL_do_handshake #define SSL_in_init wolfSSL_SSL_in_init +#define SSL_in_connect_init wolfSSL_SSL_in_connect_init #define SSL_get0_session wolfSSL_SSL_get0_session #define SSL_CTX_set_tlsext_ticket_key_cb wolfSSL_CTX_set_tlsext_ticket_key_cb #define SSL_CTX_set_tlsext_status_cb wolfSSL_CTX_set_tlsext_status_cb @@ -967,6 +1088,7 @@ enum { #define SSL_CTX_set_alpn_select_cb wolfSSL_CTX_set_alpn_select_cb #define SSL_CTX_set_next_protos_advertised_cb wolfSSL_CTX_set_next_protos_advertised_cb #define SSL_CTX_set_next_proto_select_cb wolfSSL_CTX_set_next_proto_select_cb +#define SSL_set_alpn_protos wolfSSL_set_alpn_protos #define SSL_get0_next_proto_negotiated wolfSSL_get0_next_proto_negotiated #define SSL_is_server wolfSSL_is_server #define SSL_CTX_set1_curves_list wolfSSL_CTX_set1_curves_list @@ -982,8 +1104,10 @@ enum { #define SSL_get0_param wolfSSL_get0_param #define ERR_NUM_ERRORS 16 +#define EVP_PKEY_NONE NID_undef #define EVP_PKEY_RSA 6 #define EVP_PKEY_RSA2 19 +#define EVP_PKEY_DH 28 #define SN_pkcs9_emailAddress "Email" #define LN_pkcs9_emailAddress "emailAddress" #define NID_pkcs9_emailAddress 48 diff --git a/wolfssl/openssl/x509.h b/wolfssl/openssl/x509.h index 9d1300284..bc38bf217 100644 --- a/wolfssl/openssl/x509.h +++ b/wolfssl/openssl/x509.h @@ -1,3 +1,6 @@ /* x509.h for openssl */ #include + +/* for compatibility, this is expected to be included */ +#include diff --git a/wolfssl/openssl/x509_vfy.h b/wolfssl/openssl/x509_vfy.h new file mode 100644 index 000000000..54afb6707 --- /dev/null +++ b/wolfssl/openssl/x509_vfy.h @@ -0,0 +1 @@ +/* x509_vfy.h for openssl */ diff --git a/wolfssl/openssl/x509v3.h b/wolfssl/openssl/x509v3.h index bb159a674..ba3a67f02 100644 --- a/wolfssl/openssl/x509v3.h +++ b/wolfssl/openssl/x509v3.h @@ -54,6 +54,19 @@ struct WOLFSSL_v3_ext_method { }; #define WOLFSSL_ASN1_BOOLEAN int +#define GEN_OTHERNAME 0 +#define GEN_EMAIL 1 +#define GEN_DNS 2 +#define GEN_X400 3 +#define GEN_DIRNAME 4 +#define GEN_EDIPARTY 5 +#define GEN_URI 6 +#define GEN_IPADD 7 +#define GEN_RID 8 + +#define GENERAL_NAME WOLFSSL_GENERAL_NAME + +#define X509V3_CTX WOLFSSL_X509V3_CTX struct WOLFSSL_X509_EXTENSION { WOLFSSL_ASN1_OBJECT *obj; @@ -63,11 +76,6 @@ struct WOLFSSL_X509_EXTENSION { WOLFSSL_STACK* ext_sk; /* For extension specific data */ }; -struct WOLFSSL_ACCESS_DESCRIPTION { - WOLFSSL_ASN1_OBJECT *method; - WOLFSSL_GENERAL_NAME *location; -}; - typedef struct WOLFSSL_AUTHORITY_KEYID AUTHORITY_KEYID; typedef struct WOLFSSL_BASIC_CONSTRAINTS BASIC_CONSTRAINTS; typedef struct WOLFSSL_ACCESS_DESCRIPTION ACCESS_DESCRIPTION; @@ -90,8 +98,12 @@ WOLFSSL_API int wolfSSL_X509V3_EXT_print(WOLFSSL_BIO *out, #define ASN1_OCTET_STRING WOLFSSL_ASN1_STRING #define X509V3_EXT_get wolfSSL_X509V3_EXT_get #define X509V3_EXT_d2i wolfSSL_X509V3_EXT_d2i +#define X509V3_EXT_print wolfSSL_X509V3_EXT_print #define i2s_ASN1_OCTET_STRING wolfSSL_i2s_ASN1_STRING #define X509V3_EXT_print wolfSSL_X509V3_EXT_print +#define X509V3_EXT_conf_nid wolfSSL_X509V3_EXT_conf_nid +#define X509V3_set_ctx wolfSSL_X509V3_set_ctx +#define X509V3_set_ctx_nodb wolfSSL_X509V3_set_ctx_nodb #ifdef __cplusplus } diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index a7c05217a..dd4333af2 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -119,6 +119,8 @@ typedef struct WOLFSSL_STACK WOLFSSL_STACK; typedef struct WOLFSSL_X509 WOLFSSL_X509; typedef struct WOLFSSL_X509_NAME WOLFSSL_X509_NAME; typedef struct WOLFSSL_X509_NAME_ENTRY WOLFSSL_X509_NAME_ENTRY; +typedef struct WOLFSSL_X509_PUBKEY WOLFSSL_X509_PUBKEY; +typedef struct WOLFSSL_X509_ALGOR WOLFSSL_X509_ALGOR; typedef struct WOLFSSL_X509_CHAIN WOLFSSL_X509_CHAIN; typedef struct WC_PKCS12 WOLFSSL_X509_PKCS12; @@ -171,13 +173,15 @@ typedef struct WOLFSSL_BIO WOLFSSL_BIO; typedef struct WOLFSSL_BIO_METHOD WOLFSSL_BIO_METHOD; typedef struct WOLFSSL_X509_EXTENSION WOLFSSL_X509_EXTENSION; typedef struct WOLFSSL_ASN1_TIME WOLFSSL_ASN1_TIME; -typedef struct WOLFSSL_ASN1_INTEGER WOLFSSL_ASN1_INTEGER; typedef struct WOLFSSL_ASN1_OBJECT WOLFSSL_ASN1_OBJECT; +typedef struct WOLFSSL_ASN1_OTHERNAME WOLFSSL_ASN1_OTHERNAME; +typedef struct WOLFSSL_X509V3_CTX WOLFSSL_X509V3_CTX; typedef struct WOLFSSL_ASN1_STRING WOLFSSL_ASN1_STRING; typedef struct WOLFSSL_dynlock_value WOLFSSL_dynlock_value; typedef struct WOLFSSL_DH WOLFSSL_DH; typedef struct WOLFSSL_ASN1_BIT_STRING WOLFSSL_ASN1_BIT_STRING; +typedef struct WOLFSSL_ASN1_TYPE WOLFSSL_ASN1_TYPE; typedef struct WOLFSSL_GENERAL_NAME WOLFSSL_GENERAL_NAME; typedef struct WOLFSSL_AUTHORITY_KEYID WOLFSSL_AUTHORITY_KEYID; @@ -186,18 +190,6 @@ typedef struct WOLFSSL_ACCESS_DESCRIPTION WOLFSSL_ACCESS_DESCRIPTION; #if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA) -struct WOLFSSL_GENERAL_NAME { - int type; - struct { /* derefrenced */ - WOLFSSL_ASN1_STRING* rfc822Name; - WOLFSSL_ASN1_STRING* dNSName; - WOLFSSL_ASN1_STRING* uniformResourceIdentifier; - WOLFSSL_ASN1_STRING* iPAddress; - WOLFSSL_ASN1_OBJECT* registeredID; - WOLFSSL_ASN1_STRING* ia5; - } d; -}; - struct WOLFSSL_AUTHORITY_KEYID { WOLFSSL_ASN1_STRING *keyid; WOLFSSL_ASN1_OBJECT *issuer; @@ -214,27 +206,14 @@ struct WOLFSSL_BASIC_CONSTRAINTS { #define WOLFSSL_ASN1_UTCTIME WOLFSSL_ASN1_TIME #define WOLFSSL_ASN1_GENERALIZEDTIME WOLFSSL_ASN1_TIME -#define WOLFSSL_ASN1_INTEGER_MAX 20 -struct WOLFSSL_ASN1_INTEGER { - /* size can be increased set at 20 for tag, length then to hold at least 16 - * byte type */ - unsigned char intData[WOLFSSL_ASN1_INTEGER_MAX]; - /* ASN_INTEGER | LENGTH | hex of number */ - unsigned char negative; /* negative number flag */ - - unsigned char* data; - unsigned int dataMax; /* max size of data buffer */ - unsigned int isDynamic:1; /* flag for if data pointer dynamic (1 is yes 0 is no) */ - -#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT) - int length; -#endif -}; - struct WOLFSSL_ASN1_TIME { /* MAX_DATA_SIZE is 32 */ unsigned char data[32 + 2]; /* ASN_TIME | LENGTH | date bytes */ + + /* for compat */ + word32 length; + int type; }; struct WOLFSSL_ASN1_STRING { @@ -247,6 +226,52 @@ struct WOLFSSL_ASN1_STRING { }; #define WOLFSSL_MAX_SNAME 40 + +#if defined(HAVE_EX_DATA) || defined(FORTRESS) + #define MAX_EX_DATA 5 /* allow for five items of ex_data */ +#endif + + +#define WOLFSSL_ASN1_DYNAMIC 0x1 +#define WOLFSSL_ASN1_DYNAMIC_DATA 0x2 + +struct WOLFSSL_ASN1_OTHERNAME { + WOLFSSL_ASN1_OBJECT* type_id; + WOLFSSL_ASN1_TYPE* value; +}; + +struct WOLFSSL_GENERAL_NAME { + int type; + union { + char* ptr; + WOLFSSL_ASN1_OTHERNAME* otherName; + WOLFSSL_ASN1_STRING* rfc822Name; + WOLFSSL_ASN1_STRING* dNSName; + WOLFSSL_ASN1_TYPE* x400Address; + WOLFSSL_X509_NAME* directoryName; + WOLFSSL_ASN1_STRING* uniformResourceIdentifier; + WOLFSSL_ASN1_STRING* iPAddress; + WOLFSSL_ASN1_OBJECT* registeredID; + + WOLFSSL_ASN1_STRING* ip; + WOLFSSL_X509_NAME* dirn; + WOLFSSL_ASN1_STRING* ia5; + WOLFSSL_ASN1_OBJECT* rid; + WOLFSSL_ASN1_TYPE* other; + } d; /* dereference */ +}; + +struct WOLFSSL_ACCESS_DESCRIPTION { + WOLFSSL_ASN1_OBJECT* method; + WOLFSSL_GENERAL_NAME* location; +}; + +struct WOLFSSL_X509V3_CTX { + WOLFSSL_X509* x509; +}; + + + struct WOLFSSL_ASN1_OBJECT { void* heap; const unsigned char* obj; @@ -256,13 +281,15 @@ struct WOLFSSL_ASN1_OBJECT { int grp; /* type of OID, i.e. oidCertPolicyType */ int nid; unsigned int objSz; - unsigned char dynamic; /* if 1 then obj was dynamiclly created, 0 otherwise */ - #define WOLFSSL_ASN1_DYNAMIC 0x1 - #define WOLFSSL_ASN1_DYNAMIC_DATA 0x2 #if defined(OPENSSL_ALL) || defined(WOLFSSL_QT) int ca; WOLFSSL_ASN1_INTEGER *pathlen; #endif + unsigned char dynamic; /* if 1 then obj was dynamically created, 0 otherwise */ + +#if defined(WOLFSSL_APACHE_HTTPD) + WOLFSSL_GENERAL_NAME* gn; +#endif struct d { /* derefrenced */ WOLFSSL_ASN1_STRING* dNSName; @@ -271,16 +298,40 @@ struct WOLFSSL_ASN1_OBJECT { #if defined(WOLFSSL_QT) || defined(OPENSSL_ALL) WOLFSSL_ASN1_STRING* uniformResourceIdentifier; WOLFSSL_ASN1_STRING iPAddress_internal; + WOLFSSL_ASN1_OTHERNAME* otherName; /* added for Apache httpd */ #endif WOLFSSL_ASN1_STRING* iPAddress; /* points to iPAddress_internal */ } d; }; +/* wrap ASN1 types */ +struct WOLFSSL_ASN1_TYPE { + int type; + union { + char *ptr; + WOLFSSL_ASN1_STRING* asn1_string; + WOLFSSL_ASN1_OBJECT* object; + WOLFSSL_ASN1_INTEGER* integer; + WOLFSSL_ASN1_BIT_STRING* bit_string; + WOLFSSL_ASN1_STRING* octet_string; + WOLFSSL_ASN1_STRING* printablestring; + WOLFSSL_ASN1_STRING* ia5string; + WOLFSSL_ASN1_UTCTIME* utctime; + WOLFSSL_ASN1_GENERALIZEDTIME* generalizedtime; + WOLFSSL_ASN1_STRING* utf8string; + WOLFSSL_ASN1_STRING* set; + WOLFSSL_ASN1_STRING* sequence; + } value; +}; + struct WOLFSSL_EVP_PKEY { void* heap; int type; /* openssh dereference */ int save_type; /* openssh dereference */ int pkey_sz; + int references; /*number of times free should be called for complete free*/ + wolfSSL_Mutex refMutex; /* ref count mutex */ + union { char* ptr; /* der format of key / or raw for NTRU */ } pkey; @@ -307,8 +358,34 @@ typedef char WOLFSSL_EVP_MD; #define WOLFSSL_EVP_TYPE_DEFINED #endif +struct WOLFSSL_X509_PKEY { + WOLFSSL_EVP_PKEY* dec_pkey; /* dereferenced by Apache */ + void* heap; +}; +typedef struct WOLFSSL_X509_PKEY WOLFSSL_X509_PKEY; + +struct WOLFSSL_X509_INFO { + WOLFSSL_X509 *x509; + WOLFSSL_X509_CRL *crl; + WOLFSSL_X509_PKEY *x_pkey; /* dereferenced by Apache */ + EncryptedInfo enc_cipher; + int enc_len; + char *enc_data; + int num; +}; +typedef struct WOLFSSL_X509_INFO WOLFSSL_X509_INFO; + #define WOLFSSL_EVP_PKEY_DEFAULT EVP_PKEY_RSA /* default key type */ +struct WOLFSSL_X509_ALGOR { + WOLFSSL_ASN1_OBJECT* algorithm; +}; + +struct WOLFSSL_X509_PUBKEY { + WOLFSSL_X509_ALGOR* algor; + int pubKeyOID; +}; + enum BIO_TYPE { WOLFSSL_BIO_BUFFER = 1, @@ -328,6 +405,16 @@ enum BIO_FLAGS { WOLFSSL_BIO_FLAG_RETRY = 0x10 }; +enum BIO_CB_OPS { + WOLFSSL_BIO_CB_FREE = 0x01, + WOLFSSL_BIO_CB_READ = 0x02, + WOLFSSL_BIO_CB_WRITE = 0x03, + WOLFSSL_BIO_CB_PUTS = 0x04, + WOLFSSL_BIO_CB_GETS = 0x05, + WOLFSSL_BIO_CB_CTRL = 0x06, + WOLFSSL_BIO_CB_RETURN = 0x80 +}; + typedef struct WOLFSSL_BUF_MEM { char* data; /* dereferenced */ size_t length; /* current length */ @@ -338,6 +425,12 @@ typedef struct WOLFSSL_COMP_METHOD { int type; /* stunnel dereference */ } WOLFSSL_COMP_METHOD; +typedef struct WOLFSSL_COMP { + int id; + const char *name; + WOLFSSL_COMP_METHOD *method; +} WOLFSSL_COMP; + struct WOLFSSL_X509_LOOKUP_METHOD { int type; }; @@ -397,6 +490,8 @@ typedef struct WOLFSSL_X509_OBJECT { } data; } WOLFSSL_X509_OBJECT; +#define WOLFSSL_ASN1_BOOLEAN int + typedef struct WOLFSSL_BUFFER_INFO { unsigned char* buffer; unsigned int length; @@ -414,7 +509,12 @@ typedef struct WOLFSSL_X509_STORE_CTX { WOLFSSL_X509_VERIFY_PARAM* param; /* certificate validation parameter */ #endif char* domain; /* subject CN domain name */ - void* ex_data; /* external data, for fortress build */ +#if defined(HAVE_EX_DATA) || defined(FORTRESS) + void* ex_data[MAX_EX_DATA]; /* external data */ +#endif +#if defined(WOLFSSL_APACHE_HTTPD) || defined(OPENSSL_ALL) + int depth; /* used in X509_STORE_CTX_*_depth */ +#endif void* userCtx; /* user ctx */ int error; /* current error */ int error_depth; /* index of cert depth for this error */ @@ -476,6 +576,8 @@ enum AlertLevel { typedef WOLFSSL_METHOD* (*wolfSSL_method_func)(void* heap); /* CTX Method EX Constructor Functions */ +WOLFSSL_API WOLFSSL_METHOD *wolfTLS_client_method_ex(void* heap); +WOLFSSL_API WOLFSSL_METHOD *wolfTLS_server_method_ex(void* heap); WOLFSSL_API WOLFSSL_METHOD *wolfSSLv3_server_method_ex(void* heap); WOLFSSL_API WOLFSSL_METHOD *wolfSSLv3_client_method_ex(void* heap); WOLFSSL_API WOLFSSL_METHOD *wolfTLSv1_method_ex(void* heap); @@ -510,6 +612,8 @@ WOLFSSL_API WOLFSSL_METHOD *wolfSSLv23_client_method_ex(void* heap); #endif /* CTX Method Constructor Functions */ +WOLFSSL_API WOLFSSL_METHOD *wolfTLS_client_method(void); +WOLFSSL_API WOLFSSL_METHOD *wolfTLS_server_method(void); WOLFSSL_API WOLFSSL_METHOD *wolfSSLv23_method(void); WOLFSSL_API WOLFSSL_METHOD *wolfSSLv3_server_method(void); WOLFSSL_API WOLFSSL_METHOD *wolfSSLv3_client_method(void); @@ -753,6 +857,7 @@ WOLFSSL_API int wolfSSL_get_ex_new_index(long argValue, void* arg, WOLFSSL_API void wolfSSL_CTX_set_verify(WOLFSSL_CTX*, int, VerifyCallback verify_callback); WOLFSSL_API void wolfSSL_set_verify(WOLFSSL*, int, VerifyCallback verify_callback); +WOLFSSL_API void wolfSSL_set_verify_result(WOLFSSL*, long); WOLFSSL_API void wolfSSL_SetCertCbCtx(WOLFSSL*, void*); WOLFSSL_API int wolfSSL_pending(WOLFSSL*); @@ -835,6 +940,13 @@ WOLFSSL_API const char* wolfSSL_ERR_reason_error_string(unsigned long); /* extras */ + +/* for now LHASH is not implemented */ +typedef int WOLFSSL_LHASH; +#ifndef WOLF_LHASH_OF + #define WOLF_LHASH_OF(x) WOLFSSL_LHASH +#endif + #ifndef WOLF_STACK_OF #define WOLF_STACK_OF(x) WOLFSSL_STACK #endif @@ -842,6 +954,10 @@ WOLFSSL_API const char* wolfSSL_ERR_reason_error_string(unsigned long); #define DECLARE_STACK_OF(x) WOLF_STACK_OF(x); #endif +WOLFSSL_API WOLFSSL_STACK* wolfSSL_sk_new_node(void* heap); +WOLFSSL_API void wolfSSL_sk_free_node(WOLFSSL_STACK* in); +WOLFSSL_API int wolfSSL_sk_push_node(WOLFSSL_STACK** stack, WOLFSSL_STACK* in); + #if defined(HAVE_OCSP) #include "wolfssl/ocsp.h" #include "wolfssl/wolfcrypt/asn.h" @@ -851,8 +967,6 @@ WOLFSSL_API const char* wolfSSL_ERR_reason_error_string(unsigned long); WOLFSSL_API int wolfSSL_sk_ACCESS_DESCRIPTION_push( WOLF_STACK_OF(ACCESS_DESCRIPTION)* sk, WOLFSSL_ACCESS_DESCRIPTION* access); -WOLFSSL_API void wolfSSL_sk_ACCESS_DESCRIPTION_pop_free(WOLFSSL_STACK* sk, - void f (WOLFSSL_ACCESS_DESCRIPTION*)); #endif /* defined(OPENSSL_ALL) || defined(WOLFSSL_QT) */ typedef WOLF_STACK_OF(WOLFSSL_GENERAL_NAME) WOLFSSL_GENERAL_NAMES; @@ -862,13 +976,27 @@ WOLFSSL_API int wolfSSL_sk_X509_push(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, WOLFSSL_API WOLFSSL_X509* wolfSSL_sk_X509_pop(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk); WOLFSSL_API WOLFSSL_STACK* wolfSSL_sk_X509_dup(WOLFSSL_STACK* sk); WOLFSSL_API void wolfSSL_sk_X509_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk); -WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_sk_GENERAL_NAME_value( +WOLFSSL_API WOLFSSL_GENERAL_NAME* wolfSSL_GENERAL_NAME_new(void); +WOLFSSL_API void wolfSSL_GENERAL_NAME_free(WOLFSSL_GENERAL_NAME* gn); +WOLFSSL_API int wolfSSL_sk_GENERAL_NAME_push(WOLF_STACK_OF(WOLFSSL_GENERAL_NAME)* sk, + WOLFSSL_GENERAL_NAME* gn); +WOLFSSL_API WOLFSSL_GENERAL_NAME* wolfSSL_sk_GENERAL_NAME_value( WOLFSSL_STACK* sk, int i); WOLFSSL_API int wolfSSL_sk_GENERAL_NAME_num(WOLFSSL_STACK* sk); WOLFSSL_API void wolfSSL_sk_GENERAL_NAME_pop_free(WOLFSSL_STACK* sk, void f (WOLFSSL_GENERAL_NAME*)); -WOLFSSL_API void wolfSSL_GENERAL_NAME_free(WOLFSSL_GENERAL_NAME* name); WOLFSSL_API void wolfSSL_GENERAL_NAMES_free(WOLFSSL_GENERAL_NAMES* name); +WOLFSSL_API int wolfSSL_sk_ACCESS_DESCRIPTION_num(WOLFSSL_STACK* sk); +WOLFSSL_API void wolfSSL_AUTHORITY_INFO_ACCESS_free( + WOLF_STACK_OF(WOLFSSL_ACCESS_DESCRIPTION)* sk); +WOLFSSL_API WOLFSSL_ACCESS_DESCRIPTION* wolfSSL_sk_ACCESS_DESCRIPTION_value( + WOLFSSL_STACK* sk, int idx); +WOLFSSL_API void wolfSSL_sk_ACCESS_DESCRIPTION_pop_free(WOLFSSL_STACK* sk, + void f (WOLFSSL_ACCESS_DESCRIPTION*)); +WOLFSSL_API void wolfSSL_sk_X509_EXTENSION_pop_free( + WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* sk, + void f (WOLFSSL_X509_EXTENSION*)); +WOLFSSL_API WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* wolfSSL_sk_X509_EXTENSION_new_null(void); WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_ASN1_OBJECT_new(void); WOLFSSL_API void wolfSSL_ASN1_OBJECT_free(WOLFSSL_ASN1_OBJECT* obj); WOLFSSL_API WOLFSSL_STACK* wolfSSL_sk_new_asn1_obj(void); @@ -881,7 +1009,9 @@ WOLFSSL_API void wolfSSL_sk_ASN1_OBJECT_pop_free( WOLF_STACK_OF(WOLFSSL_ASN1_OBJECT)* sk, void (*func)(WOLFSSL_ASN1_OBJECT*)); WOLFSSL_API int wolfSSL_ASN1_STRING_to_UTF8(unsigned char **out, WOLFSSL_ASN1_STRING *in); - +WOLFSSL_API int wolfSSL_sk_X509_EXTENSION_num(WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* sk); +WOLFSSL_API WOLFSSL_X509_EXTENSION* wolfSSL_sk_X509_EXTENSION_value( + WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* sk, int idx); WOLFSSL_API int wolfSSL_set_ex_data(WOLFSSL*, int, void*); WOLFSSL_API int wolfSSL_get_shutdown(const WOLFSSL*); WOLFSSL_API int wolfSSL_set_rfd(WOLFSSL*, int); @@ -900,6 +1030,7 @@ WOLFSSL_API int wolfSSL_get_current_cipher_suite(WOLFSSL* ssl); WOLFSSL_API WOLFSSL_CIPHER* wolfSSL_get_current_cipher(WOLFSSL*); WOLFSSL_API char* wolfSSL_CIPHER_description(const WOLFSSL_CIPHER*, char*, int); WOLFSSL_API const char* wolfSSL_CIPHER_get_name(const WOLFSSL_CIPHER* cipher); +WOLFSSL_API const char* wolfSSL_CIPHER_get_version(const WOLFSSL_CIPHER* cipher); WOLFSSL_API const char* wolfSSL_SESSION_CIPHER_get_name(WOLFSSL_SESSION* session); WOLFSSL_API const char* wolfSSL_get_cipher(WOLFSSL*); WOLFSSL_API void wolfSSL_sk_CIPHER_free(WOLF_STACK_OF(WOLFSSL_CIPHER)* sk); @@ -907,6 +1038,10 @@ WOLFSSL_API WOLFSSL_SESSION* wolfSSL_get1_session(WOLFSSL* ssl); /* what's ref count */ WOLFSSL_API WOLFSSL_X509* wolfSSL_X509_new(void); +#if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL) +WOLFSSL_API int wolfSSL_X509_up_ref(WOLFSSL_X509* x509); +WOLFSSL_API int wolfSSL_EVP_PKEY_up_ref(WOLFSSL_EVP_PKEY* pkey); +#endif WOLFSSL_API int wolfSSL_OCSP_parse_url(char* url, char** host, char** port, char** path, int* ssl); @@ -917,8 +1052,10 @@ WOLFSSL_API WOLFSSL_METHOD* wolfSSLv2_server_method(void); WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_new(WOLFSSL_BIO_METHOD*); WOLFSSL_API int wolfSSL_BIO_free(WOLFSSL_BIO*); +WOLFSSL_API void wolfSSL_BIO_vfree(WOLFSSL_BIO*); WOLFSSL_API int wolfSSL_BIO_free_all(WOLFSSL_BIO*); WOLFSSL_API int wolfSSL_BIO_gets(WOLFSSL_BIO* bio, char* buf, int sz); +WOLFSSL_API int wolfSSL_BIO_puts(WOLFSSL_BIO* bio, const char* buf); WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_next(WOLFSSL_BIO* bio); WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_find_type(WOLFSSL_BIO* bio, int type); WOLFSSL_API int wolfSSL_BIO_read(WOLFSSL_BIO*, void*, int); @@ -928,6 +1065,14 @@ WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_pop(WOLFSSL_BIO*); WOLFSSL_API int wolfSSL_BIO_flush(WOLFSSL_BIO*); WOLFSSL_API int wolfSSL_BIO_pending(WOLFSSL_BIO*); +typedef long (*wolf_bio_info_cb)(WOLFSSL_BIO *bio, int event, const char *parg, + int iarg, long larg, long return_value); +WOLFSSL_API void wolfSSL_BIO_set_callback(WOLFSSL_BIO *bio, + wolf_bio_info_cb callback_func); +WOLFSSL_API wolf_bio_info_cb wolfSSL_BIO_get_callback(WOLFSSL_BIO *bio); +WOLFSSL_API void wolfSSL_BIO_set_callback_arg(WOLFSSL_BIO *bio, char *arg); +WOLFSSL_API char* wolfSSL_BIO_get_callback_arg(const WOLFSSL_BIO *bio); + WOLFSSL_API WOLFSSL_BIO_METHOD* wolfSSL_BIO_f_buffer(void); WOLFSSL_API long wolfSSL_BIO_set_write_buffer_size(WOLFSSL_BIO*, long size); WOLFSSL_API WOLFSSL_BIO_METHOD* wolfSSL_BIO_f_ssl(void); @@ -937,8 +1082,33 @@ WOLFSSL_API int wolfSSL_BIO_eof(WOLFSSL_BIO*); WOLFSSL_API WOLFSSL_BIO_METHOD* wolfSSL_BIO_s_mem(void); WOLFSSL_API WOLFSSL_BIO_METHOD* wolfSSL_BIO_f_base64(void); WOLFSSL_API void wolfSSL_BIO_set_flags(WOLFSSL_BIO*, int); +WOLFSSL_API long wolfSSL_BIO_set_nbio(WOLFSSL_BIO*, long); WOLFSSL_API int wolfSSL_BIO_get_mem_data(WOLFSSL_BIO* bio,void* p); + +WOLFSSL_API void wolfSSL_BIO_set_init(WOLFSSL_BIO*, int); +WOLFSSL_API void wolfSSL_BIO_set_data(WOLFSSL_BIO*, void*); +WOLFSSL_API void* wolfSSL_BIO_get_data(WOLFSSL_BIO*); +WOLFSSL_API void wolfSSL_BIO_set_shutdown(WOLFSSL_BIO*, int); +WOLFSSL_API int wolfSSL_BIO_get_shutdown(WOLFSSL_BIO*); +WOLFSSL_API int wolfSSL_BIO_clear_retry_flags(WOLFSSL_BIO*); + +WOLFSSL_API WOLFSSL_BIO_METHOD *wolfSSL_BIO_meth_new(int, const char*); +WOLFSSL_API void wolfSSL_BIO_meth_free(WOLFSSL_BIO_METHOD*); +typedef int (*wolfSSL_BIO_meth_write_cb)(WOLFSSL_BIO*, const char*, int); +WOLFSSL_API int wolfSSL_BIO_meth_set_write(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_write_cb); +typedef int (*wolfSSL_BIO_meth_read_cb)(WOLFSSL_BIO *, char *, int); +WOLFSSL_API int wolfSSL_BIO_meth_set_read(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_read_cb); +typedef int (*wolfSSL_BIO_meth_puts_cb)(WOLFSSL_BIO*, const char*); +WOLFSSL_API int wolfSSL_BIO_meth_set_puts(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_puts_cb); +typedef int (*wolfSSL_BIO_meth_gets_cb)(WOLFSSL_BIO*, char*, int); +WOLFSSL_API int wolfSSL_BIO_meth_set_gets(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_gets_cb); +typedef long (*wolfSSL_BIO_meth_get_ctrl_cb)(WOLFSSL_BIO*, int, long, void*); +WOLFSSL_API int wolfSSL_BIO_meth_set_ctrl(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_get_ctrl_cb); +typedef int (*wolfSSL_BIO_meth_create_cb)(WOLFSSL_BIO*); +WOLFSSL_API int wolfSSL_BIO_meth_set_create(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_create_cb); +typedef int (*wolfSSL_BIO_meth_destroy_cb)(WOLFSSL_BIO*); +WOLFSSL_API int wolfSSL_BIO_meth_set_destroy(WOLFSSL_BIO_METHOD*, wolfSSL_BIO_meth_destroy_cb); WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_new_mem_buf(void* buf, int len); @@ -1025,7 +1195,21 @@ WOLFSSL_API unsigned char* wolfSSL_X509_get_subjectKeyID( WOLFSSL_API int wolfSSL_X509_verify(WOLFSSL_X509* x509, WOLFSSL_EVP_PKEY* pkey); WOLFSSL_API int wolfSSL_X509_set_subject_name(WOLFSSL_X509*, WOLFSSL_X509_NAME*); +WOLFSSL_API int wolfSSL_X509_set_issuer_name(WOLFSSL_X509*, + WOLFSSL_X509_NAME*); WOLFSSL_API int wolfSSL_X509_set_pubkey(WOLFSSL_X509*, WOLFSSL_EVP_PKEY*); +WOLFSSL_API int wolfSSL_X509_set_notAfter(WOLFSSL_X509* x509, + const WOLFSSL_ASN1_TIME* t); +WOLFSSL_API int wolfSSL_X509_set_notBefore(WOLFSSL_X509* x509, + const WOLFSSL_ASN1_TIME* t); +WOLFSSL_API WOLFSSL_ASN1_TIME* wolfSSL_X509_get_notBefore(WOLFSSL_X509* x509); +WOLFSSL_API WOLFSSL_ASN1_TIME* wolfSSL_X509_get_notAfter(WOLFSSL_X509* x509); +WOLFSSL_API int wolfSSL_X509_set_serialNumber(WOLFSSL_X509* x509, + WOLFSSL_ASN1_INTEGER* s); +WOLFSSL_API int wolfSSL_X509_set_version(WOLFSSL_X509* x509, long v); +WOLFSSL_API int wolfSSL_X509_sign(WOLFSSL_X509* x509, WOLFSSL_EVP_PKEY* pkey, + const WOLFSSL_EVP_MD* md); + WOLFSSL_API int wolfSSL_X509_NAME_entry_count(WOLFSSL_X509_NAME*); WOLFSSL_API int wolfSSL_X509_NAME_get_text_by_NID( @@ -1037,6 +1221,7 @@ WOLFSSL_API WOLFSSL_ASN1_STRING* wolfSSL_X509_NAME_ENTRY_get_data(WOLFSSL_X509_N WOLFSSL_API WOLFSSL_ASN1_STRING* wolfSSL_ASN1_STRING_new(void); WOLFSSL_API WOLFSSL_ASN1_STRING* wolfSSL_ASN1_STRING_type_new(int type); WOLFSSL_API int wolfSSL_ASN1_STRING_type(const WOLFSSL_ASN1_STRING* asn1); +WOLFSSL_API WOLFSSL_ASN1_STRING* wolfSSL_d2i_DISPLAYTEXT(WOLFSSL_ASN1_STRING **asn, unsigned char **in, long len); WOLFSSL_API void wolfSSL_ASN1_STRING_free(WOLFSSL_ASN1_STRING* asn1); WOLFSSL_API int wolfSSL_ASN1_STRING_set(WOLFSSL_ASN1_STRING* asn1, const void* data, int dataSz); @@ -1093,6 +1278,8 @@ WOLFSSL_API WOLFSSL_EVP_PKEY* wolfSSL_d2i_PrivateKey(int type, WOLFSSL_EVP_PKEY** out, const unsigned char **in, long inSz); WOLFSSL_API WOLFSSL_EVP_PKEY* wolfSSL_d2i_PrivateKey_EVP(WOLFSSL_EVP_PKEY** key, unsigned char** in, long inSz); +WOLFSSL_API int wolfSSL_i2d_PrivateKey(WOLFSSL_EVP_PKEY* key, + unsigned char** der); WOLFSSL_API WOLFSSL_EVP_PKEY* wolfSSL_PKEY_new_ex(void* heap); WOLFSSL_API WOLFSSL_EVP_PKEY* wolfSSL_PKEY_new(void); WOLFSSL_API int wolfSSL_X509_cmp_current_time(const WOLFSSL_ASN1_TIME*); @@ -1141,8 +1328,24 @@ WOLFSSL_API WOLF_STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_SSL_CTX_get_client_CA_list const WOLFSSL_CTX *s); WOLFSSL_API void wolfSSL_CTX_set_client_CA_list(WOLFSSL_CTX*, WOLF_STACK_OF(WOLFSSL_X509_NAME)*); -WOLFSSL_API void* wolfSSL_X509_STORE_CTX_get_ex_data(WOLFSSL_X509_STORE_CTX*, int); -WOLFSSL_API int wolfSSL_get_ex_data_X509_STORE_CTX_idx(void); +WOLFSSL_API WOLF_STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_get_client_CA_list( + const WOLFSSL* ssl); + +typedef int (*client_cert_cb)(WOLFSSL *ssl, WOLFSSL_X509 **x509, + WOLFSSL_EVP_PKEY **pkey); +WOLFSSL_API void wolfSSL_CTX_set_client_cert_cb(WOLFSSL_CTX *ctx, client_cert_cb); + +WOLFSSL_API void* wolfSSL_X509_STORE_CTX_get_ex_data( + WOLFSSL_X509_STORE_CTX* ctx, int idx); +WOLFSSL_API int wolfSSL_X509_STORE_CTX_set_ex_data(WOLFSSL_X509_STORE_CTX* ctx, + int idx, void *data); +WOLFSSL_API void wolfSSL_X509_STORE_CTX_set_depth(WOLFSSL_X509_STORE_CTX* ctx, + int depth); +WOLFSSL_API WOLFSSL_X509* wolfSSL_X509_STORE_CTX_get0_current_issuer( + WOLFSSL_X509_STORE_CTX* ctx); +WOLFSSL_API WOLFSSL_X509_STORE* wolfSSL_X509_STORE_CTX_get0_store( + WOLFSSL_X509_STORE_CTX* ctx); +WOLFSSL_API int wolfSSL_get_ex_data_X509_STORE_CTX_idx(void); WOLFSSL_API void wolfSSL_X509_STORE_CTX_set_error( WOLFSSL_X509_STORE_CTX* ctx, int er); WOLFSSL_API void* wolfSSL_get_ex_data(const WOLFSSL*, int); @@ -1209,6 +1412,7 @@ WOLFSSL_API long wolfSSL_get_options(const WOLFSSL *s); WOLFSSL_API long wolfSSL_clear_options(WOLFSSL *s, long op); WOLFSSL_API long wolfSSL_clear_num_renegotiations(WOLFSSL *s); WOLFSSL_API long wolfSSL_total_renegotiations(WOLFSSL *s); +WOLFSSL_API long wolfSSL_num_renegotiations(WOLFSSL* s); WOLFSSL_API long wolfSSL_set_tmp_dh(WOLFSSL *s, WOLFSSL_DH *dh); WOLFSSL_API long wolfSSL_set_tlsext_debug_arg(WOLFSSL *s, void *arg); WOLFSSL_API long wolfSSL_set_tlsext_status_type(WOLFSSL *s, int type); @@ -1249,9 +1453,8 @@ enum { SSL_OP_TLS_ROLLBACK_BUG = 0x00000200, SSL_OP_ALL = 0x00000400, SSL_OP_EPHEMERAL_RSA = 0x00000800, - SSL_OP_NO_SSLv2 = 0x00000000, /* N/A */ - SSL_OP_NO_SSLv3 = 0x00001000, - SSL_OP_NO_TLSv1 = 0x00002000, + WOLFSSL_OP_NO_SSLv3 = 0x00001000, + WOLFSSL_OP_NO_TLSv1 = 0x00002000, SSL_OP_PKCS1_CHECK_1 = 0x00004000, SSL_OP_PKCS1_CHECK_2 = 0x00008000, SSL_OP_NETSCAPE_CA_DN_BUG = 0x00010000, @@ -1264,12 +1467,23 @@ enum { SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION = 0x00800000, SSL_OP_SINGLE_ECDH_USE = 0x01000000, SSL_OP_CIPHER_SERVER_PREFERENCE = 0x02000000, - SSL_OP_NO_TLSv1_1 = 0x04000000, - SSL_OP_NO_TLSv1_2 = 0x08000000, + WOLFSSL_OP_NO_TLSv1_1 = 0x04000000, + WOLFSSL_OP_NO_TLSv1_2 = 0x08000000, SSL_OP_NO_COMPRESSION = 0x10000000, - SSL_OP_NO_TLSv1_3 = 0x20000000, + WOLFSSL_OP_NO_TLSv1_3 = 0x20000000, + WOLFSSL_OP_NO_SSLv2 = 0x40000000, }; +/* for compatibility these must be macros */ +#define SSL_OP_NO_SSLv2 WOLFSSL_OP_NO_SSLv2 +#define SSL_OP_NO_SSLv3 WOLFSSL_OP_NO_SSLv3 +#define SSL_OP_NO_TLSv1 WOLFSSL_OP_NO_TLSv1 +#define SSL_OP_NO_TLSv1_1 WOLFSSL_OP_NO_TLSv1_1 +#define SSL_OP_NO_TLSv1_2 WOLFSSL_OP_NO_TLSv1_2 +#if !(!defined(WOLFSSL_TLS13) && defined(WOLFSSL_APACHE_HTTPD)) /* apache uses this to determine if TLS 1.3 is enabled */ +#define SSL_OP_NO_TLSv1_3 WOLFSSL_OP_NO_TLSv1_3 +#endif + #define SSL_OP_NO_SSL_MASK (SSL_OP_NO_SSLv3 | SSL_OP_NO_TLSv1 | \ SSL_OP_NO_TLSv1_1 | SSL_OP_NO_TLSv1_2 | SSL_OP_NO_TLSv1_3) @@ -1277,7 +1491,6 @@ enum { #define SSL_WRITING 2 #define SSL_READING 3 - enum { #ifdef HAVE_OCSP /* OCSP Flags */ @@ -1382,6 +1595,7 @@ enum { X509_V_ERR_INVALID_POLICY_EXTENSION, X509_V_ERR_NO_EXPLICIT_POLICY, X509_V_ERR_UNNESTED_RESOURCE, + X509_V_ERR_APPLICATION_VERIFICATION, X509_R_CERT_ALREADY_IN_HASH_TABLE, @@ -1407,6 +1621,7 @@ WOLFSSL_API void wolfSSL_ERR_print_errors_fp(XFILE, int err); WOLFSSL_API void wolfSSL_ERR_dump_errors_fp(XFILE fp); #endif #endif +WOLFSSL_API void wolfSSL_ERR_print_errors(WOLFSSL_BIO *bio); #ifndef NO_OLD_SSL_NAMES @@ -1457,7 +1672,6 @@ WOLFSSL_API void wolfSSL_ERR_dump_errors_fp(XFILE fp); #define SSL_SENT_SHUTDOWN WOLFSSL_SENT_SHUTDOWN #define SSL_RECEIVED_SHUTDOWN WOLFSSL_RECEIVED_SHUTDOWN #define SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER WOLFSSL_MODE_ACCEPT_MOVING_WRITE_BUFFER - #define SSL_OP_NO_SSLv2 WOLFSSL_OP_NO_SSLv2 #define SSL_R_SSL_HANDSHAKE_FAILURE WOLFSSL_R_SSL_HANDSHAKE_FAILURE #define SSL_R_TLSV1_ALERT_UNKNOWN_CA WOLFSSL_R_TLSV1_ALERT_UNKNOWN_CA @@ -1515,7 +1729,6 @@ enum { /* ssl Constants */ WOLFSSL_SENT_SHUTDOWN = 1, WOLFSSL_RECEIVED_SHUTDOWN = 2, WOLFSSL_MODE_ACCEPT_MOVING_WRITE_BUFFER = 4, - WOLFSSL_OP_NO_SSLv2 = 8, WOLFSSL_R_SSL_HANDSHAKE_FAILURE = 101, WOLFSSL_R_TLSV1_ALERT_UNKNOWN_CA = 102, @@ -1632,11 +1845,17 @@ WOLFSSL_API int wolfSSL_want_read(WOLFSSL*); WOLFSSL_API int wolfSSL_want_write(WOLFSSL*); WOLFSSL_API int wolfSSL_BIO_printf(WOLFSSL_BIO*, const char*, ...); +WOLFSSL_API int wolfSSL_BIO_dump(WOLFSSL_BIO *bio, const char*, int); WOLFSSL_API int wolfSSL_ASN1_UTCTIME_print(WOLFSSL_BIO*, const WOLFSSL_ASN1_UTCTIME*); WOLFSSL_API int wolfSSL_ASN1_GENERALIZEDTIME_print(WOLFSSL_BIO*, const WOLFSSL_ASN1_GENERALIZEDTIME*); WOLFSSL_API void wolfSSL_ASN1_GENERALIZEDTIME_free(WOLFSSL_ASN1_GENERALIZEDTIME*); +WOLFSSL_API int wolfSSL_ASN1_TIME_check(const WOLFSSL_ASN1_TIME*); +WOLFSSL_API int wolfSSL_ASN1_TIME_diff(int *pday, int *psec, + const WOLFSSL_ASN1_TIME *from, const WOLFSSL_ASN1_TIME *to); +WOLFSSL_API WOLFSSL_ASN1_TIME *wolfSSL_ASN1_TIME_set(WOLFSSL_ASN1_TIME *s, time_t t); + WOLFSSL_API int wolfSSL_sk_num(WOLF_STACK_OF(WOLFSSL_ASN1_OBJECT)*); WOLFSSL_API void* wolfSSL_sk_value(WOLF_STACK_OF(WOLFSSL_ASN1_OBJECT)*, int); @@ -2605,6 +2824,7 @@ WOLFSSL_API int wolfSSL_CTX_UseSecureRenegotiation(WOLFSSL_CTX* ctx); WOLFSSL_API int wolfSSL_StartSecureRenegotiation(WOLFSSL* ssl, int resume); WOLFSSL_API int wolfSSL_Rehandshake(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_SecureResume(WOLFSSL* ssl); +WOLFSSL_API long wolfSSL_SSL_get_secure_renegotiation_support(WOLFSSL* ssl); #endif @@ -2780,18 +3000,23 @@ WOLFSSL_API int wolfSSL_OBJ_obj2nid(const WOLFSSL_ASN1_OBJECT *o); WOLFSSL_API int wolfSSL_OBJ_sn2nid(const char *sn); WOLFSSL_API char* wolfSSL_OBJ_nid2ln(int n); +WOLFSSL_API int wolfSSL_OBJ_cmp(const WOLFSSL_ASN1_OBJECT* a, + const WOLFSSL_ASN1_OBJECT* b); WOLFSSL_API int wolfSSL_OBJ_txt2nid(const char *sn); +WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_txt2obj(const char* s, int no_name); WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_nid2obj(int n); WOLFSSL_LOCAL WOLFSSL_ASN1_OBJECT* wolfSSL_OBJ_nid2obj_ex(int n, WOLFSSL_ASN1_OBJECT *arg_obj); WOLFSSL_API int wolfSSL_OBJ_obj2txt(char *buf, int buf_len, WOLFSSL_ASN1_OBJECT *a, int no_name); WOLFSSL_API void wolfSSL_OBJ_cleanup(void); +WOLFSSL_API int wolfSSL_OBJ_create(const char *oid, const char *sn, const char *ln); /* end of object functions */ WOLFSSL_API unsigned long wolfSSL_ERR_peek_last_error_line(const char **file, int *line); WOLFSSL_API long wolfSSL_ctrl(WOLFSSL* ssl, int cmd, long opt, void* pt); WOLFSSL_API long wolfSSL_CTX_ctrl(WOLFSSL_CTX* ctx, int cmd, long opt,void* pt); +WOLFSSL_API long wolfSSL_CTX_clear_extra_chain_certs(WOLFSSL_CTX* ctx); #ifndef NO_CERTS WOLFSSL_API WOLFSSL_X509_NAME_ENTRY* wolfSSL_X509_NAME_ENTRY_create_by_NID( @@ -2805,11 +3030,20 @@ WOLFSSL_API int wolfSSL_X509_NAME_add_entry_by_txt(WOLFSSL_X509_NAME *name, WOLFSSL_API int wolfSSL_X509_NAME_cmp(const WOLFSSL_X509_NAME* x, const WOLFSSL_X509_NAME* y); WOLFSSL_API WOLFSSL_X509_NAME* wolfSSL_X509_NAME_new(void); +WOLFSSL_X509_NAME* wolfSSL_X509_NAME_dup(WOLFSSL_X509_NAME* name); WOLFSSL_API int wolfSSL_check_private_key(const WOLFSSL* ssl); WOLFSSL_API void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, int nid, int* c, int* idx); -WOLFSSL_API int wolfSSL_X509_get_ext_by_NID(const WOLFSSL_X509* x509, - int nid, int lastPos); +WOLFSSL_API int wolfSSL_X509_get_ext_count(const WOLFSSL_X509* passedCert); +WOLFSSL_API int wolfSSL_X509_get_ext_by_NID(const WOLFSSL_X509 *x, int nid, int lastpos); +WOLFSSL_API int wolfSSL_X509_add_ext(WOLFSSL_X509 *x, WOLFSSL_X509_EXTENSION *ex, int loc); +WOLFSSL_API WOLFSSL_X509_EXTENSION* wolfSSL_X509V3_EXT_conf_nid( + WOLF_LHASH_OF(CONF_VALUE)* conf, WOLFSSL_X509V3_CTX* ctx, int nid, + char* value); +WOLFSSL_API void wolfSSL_X509V3_set_ctx(WOLFSSL_X509V3_CTX* ctx, + WOLFSSL_X509* issuer, WOLFSSL_X509* subject, WOLFSSL_X509* req, + WOLFSSL_X509_CRL* crl, int flag); +WOLFSSL_API void wolfSSL_X509V3_set_ctx_nodb(WOLFSSL_X509V3_CTX* ctx); WOLFSSL_API int wolfSSL_X509_digest(const WOLFSSL_X509* x509, const WOLFSSL_EVP_MD* digest, unsigned char* buf, unsigned int* len); WOLFSSL_API int wolfSSL_use_certificate(WOLFSSL* ssl, WOLFSSL_X509* x509); @@ -2828,10 +3062,7 @@ WOLFSSL_API int wolfSSL_CTX_use_PrivateKey_ASN1(int pri, WOLFSSL_CTX* ctx, WOLFSSL_API int wolfSSL_X509_cmp(const WOLFSSL_X509* a, const WOLFSSL_X509* b); WOLFSSL_API WOLFSSL_X509_EXTENSION* wolfSSL_X509_get_ext(const WOLFSSL_X509* x, int loc); WOLFSSL_API WOLFSSL_X509_EXTENSION* wolfSSL_X509_set_ext(WOLFSSL_X509* x, int loc); -WOLFSSL_API int wolfSSL_X509_get_ext_count(const WOLFSSL_X509* passed_cert); -WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_X509_EXTENSION_get_object(WOLFSSL_X509_EXTENSION* ex); WOLFSSL_API int wolfSSL_X509_EXTENSION_get_critical(const WOLFSSL_X509_EXTENSION* ex); -WOLFSSL_API WOLFSSL_ASN1_STRING* wolfSSL_X509_EXTENSION_get_data(WOLFSSL_X509_EXTENSION* ex); WOLFSSL_API WOLFSSL_X509_EXTENSION* wolfSSL_X509_EXTENSION_new(void); WOLFSSL_API int wolfSSL_sk_X509_EXTENSION_push(WOLFSSL_STACK* sk, WOLFSSL_X509_EXTENSION* ext); @@ -2840,6 +3071,8 @@ WOLFSSL_API void wolfSSL_X509_EXTENSION_free(WOLFSSL_X509_EXTENSION* ext_to_free WOLFSSL_API WOLFSSL_STACK* wolfSSL_sk_new_x509_ext(void); #endif +WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_X509_EXTENSION_get_object(WOLFSSL_X509_EXTENSION* ext); +WOLFSSL_API WOLFSSL_ASN1_STRING* wolfSSL_X509_EXTENSION_get_data(WOLFSSL_X509_EXTENSION* ext); #endif /* NO_CERTS */ WOLFSSL_API WOLFSSL_DH *wolfSSL_DSA_dup_DH(const WOLFSSL_DSA *r); @@ -2863,12 +3096,20 @@ WOLFSSL_API size_t wolfSSL_BIO_wpending(const WOLFSSL_BIO *bio); WOLFSSL_API size_t wolfSSL_BIO_ctrl_pending(WOLFSSL_BIO *b); WOLFSSL_API size_t wolfSSL_get_server_random(const WOLFSSL *ssl, unsigned char *out, size_t outlen); +WOLFSSL_API int wolfSSL_get_server_tmp_key(const WOLFSSL*, WOLFSSL_EVP_PKEY**); + +WOLFSSL_API int wolfSSL_CTX_set_min_proto_version(WOLFSSL_CTX*, int); +WOLFSSL_API int wolfSSL_CTX_set_max_proto_version(WOLFSSL_CTX*, int); + WOLFSSL_API size_t wolfSSL_get_client_random(const WOLFSSL* ssl, unsigned char* out, size_t outSz); WOLFSSL_API int wolfSSL_CTX_use_PrivateKey(WOLFSSL_CTX *ctx, WOLFSSL_EVP_PKEY *pkey); WOLFSSL_API WOLFSSL_X509 *wolfSSL_PEM_read_bio_X509(WOLFSSL_BIO *bp, WOLFSSL_X509 **x, pem_password_cb *cb, void *u); WOLFSSL_API WOLFSSL_X509 *wolfSSL_PEM_read_bio_X509_AUX (WOLFSSL_BIO *bp, WOLFSSL_X509 **x, pem_password_cb *cb, void *u); +WOLFSSL_API WOLF_STACK_OF(WOLFSSL_X509_INFO)* wolfSSL_PEM_X509_INFO_read_bio( + WOLFSSL_BIO* bio, WOLF_STACK_OF(WOLFSSL_X509_INFO)* sk, + pem_password_cb* cb, void* u); #ifndef NO_FILESYSTEM WOLFSSL_API WOLFSSL_X509_CRL *wolfSSL_PEM_read_X509_CRL(XFILE fp, WOLFSSL_X509_CRL **x, pem_password_cb *cb, void *u); @@ -2907,7 +3148,6 @@ WOLFSSL_API void* wolfSSL_get_app_data( const WOLFSSL *ssl); WOLFSSL_API int wolfSSL_set_app_data(WOLFSSL *ssl, void *arg); WOLFSSL_API WOLFSSL_ASN1_OBJECT * wolfSSL_X509_NAME_ENTRY_get_object(WOLFSSL_X509_NAME_ENTRY *ne); WOLFSSL_API WOLFSSL_X509_NAME_ENTRY *wolfSSL_X509_NAME_get_entry(WOLFSSL_X509_NAME *name, int loc); -WOLFSSL_API void wolfSSL_sk_X509_NAME_pop_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)* sk, void f (WOLFSSL_X509_NAME*)); WOLFSSL_API unsigned char *wolfSSL_SHA1(const unsigned char *d, size_t n, unsigned char *md); WOLFSSL_API unsigned char *wolfSSL_SHA256(const unsigned char *d, size_t n, unsigned char *md); WOLFSSL_API unsigned char *wolfSSL_SHA384(const unsigned char *d, size_t n, unsigned char *md); @@ -2934,6 +3174,9 @@ WOLFSSL_API long wolfSSL_BIO_get_fp(WOLFSSL_BIO *bio, XFILE* fp); || defined(OPENSSL_EXTRA) WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_new_file(const char *filename, const char *mode); +#ifndef NO_FILESYSTEM +WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_new_fp(XFILE fp, int close_flag); +#endif WOLFSSL_API long wolfSSL_CTX_set_tmp_dh(WOLFSSL_CTX*, WOLFSSL_DH*); WOLFSSL_API WOLFSSL_DH *wolfSSL_PEM_read_bio_DHparams(WOLFSSL_BIO *bp, WOLFSSL_DH **x, pem_password_cb *cb, void *u); @@ -2950,6 +3193,8 @@ WOLFSSL_API WOLFSSL_X509* wolfSSL_X509_REQ_new(void); WOLFSSL_API void wolfSSL_X509_REQ_free(WOLFSSL_X509* req); WOLFSSL_API int wolfSSL_X509_REQ_sign(WOLFSSL_X509 *req, WOLFSSL_EVP_PKEY *pkey, const WOLFSSL_EVP_MD *md); +WOLFSSL_API int wolfSSL_X509_REQ_add_extensions(WOLFSSL_X509* req, + WOLF_STACK_OF(WOLFSSL_X509_EXTENSION)* ext); WOLFSSL_API int wolfSSL_X509_REQ_set_subject_name(WOLFSSL_X509 *req, WOLFSSL_X509_NAME *name); WOLFSSL_API int wolfSSL_X509_REQ_set_pubkey(WOLFSSL_X509 *req, @@ -2974,7 +3219,15 @@ WOLFSSL_API int wolfSSL_CRYPTO_set_mem_ex_functions(void *(*m) (size_t, const ch WOLFSSL_API void wolfSSL_CRYPTO_cleanup_all_ex_data(void); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_768_prime(WOLFSSL_BIGNUM* bn); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_1024_prime(WOLFSSL_BIGNUM* bn); WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_1536_prime(WOLFSSL_BIGNUM* bn); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_2048_prime(WOLFSSL_BIGNUM* bn); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_3072_prime(WOLFSSL_BIGNUM* bn); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_4096_prime(WOLFSSL_BIGNUM* bn); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_6144_prime(WOLFSSL_BIGNUM* bn); +WOLFSSL_API WOLFSSL_BIGNUM* wolfSSL_DH_8192_prime(WOLFSSL_BIGNUM* bn); + WOLFSSL_API WOLFSSL_DH *wolfSSL_DH_generate_parameters(int prime_len, int generator, void (*callback) (int, int, void *), void *cb_arg); @@ -2993,11 +3246,41 @@ WOLFSSL_API int wolfSSL_RAND_set_rand_method(const void *meth); WOLFSSL_API int wolfSSL_CIPHER_get_bits(const WOLFSSL_CIPHER *c, int *alg_bits); -WOLFSSL_API int wolfSSL_sk_X509_NAME_num(const WOLF_STACK_OF(WOLFSSL_X509_NAME) *s); - WOLFSSL_API WOLFSSL_STACK* wolfSSL_sk_X509_new(void); WOLFSSL_API int wolfSSL_sk_X509_num(const WOLF_STACK_OF(WOLFSSL_X509) *s); +WOLFSSL_API WOLFSSL_X509_INFO *wolfSSL_X509_INFO_new(void); +WOLFSSL_API void wolfSSL_X509_INFO_free(WOLFSSL_X509_INFO* info); + +WOLFSSL_API WOLFSSL_STACK* wolfSSL_sk_X509_INFO_new_null(void); +WOLFSSL_API int wolfSSL_sk_X509_INFO_num(const WOLF_STACK_OF(WOLFSSL_X509_INFO)*); +WOLFSSL_API WOLFSSL_X509_INFO* wolfSSL_sk_X509_INFO_value( + const WOLF_STACK_OF(WOLFSSL_X509_INFO)*, int); +WOLFSSL_API int wolfSSL_sk_X509_INFO_push(WOLF_STACK_OF(WOLFSSL_X509_INFO)*, + WOLFSSL_X509_INFO*); +WOLFSSL_API WOLFSSL_X509_INFO* wolfSSL_sk_X509_INFO_pop(WOLF_STACK_OF(WOLFSSL_X509_INFO)*); +WOLFSSL_API void wolfSSL_sk_X509_INFO_pop_free(WOLF_STACK_OF(WOLFSSL_X509_INFO)*, + void f (WOLFSSL_X509_INFO*)); +WOLFSSL_API void wolfSSL_sk_X509_INFO_free(WOLF_STACK_OF(WOLFSSL_X509_INFO)*); + +typedef int (*wolf_sk_compare_cb)(const void* const *a, + const void* const *b); +WOLFSSL_API WOLF_STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_sk_X509_NAME_new( + wolf_sk_compare_cb); +WOLFSSL_API int wolfSSL_sk_X509_NAME_push(WOLF_STACK_OF(WOLFSSL_X509_NAME)*, + WOLFSSL_X509_NAME*); +WOLFSSL_API int wolfSSL_sk_X509_NAME_find(const WOLF_STACK_OF(WOLFSSL_X509_NAME)*, + WOLFSSL_X509_NAME*); +WOLFSSL_API int wolfSSL_sk_X509_NAME_set_cmp_func( + WOLF_STACK_OF(WOLFSSL_X509_NAME)*, wolf_sk_compare_cb); +WOLFSSL_API WOLFSSL_X509_NAME* wolfSSL_sk_X509_NAME_value(const WOLF_STACK_OF(WOLFSSL_X509_NAME)*, int); +WOLFSSL_API int wolfSSL_sk_X509_NAME_num(const WOLF_STACK_OF(WOLFSSL_X509_NAME)*); +WOLFSSL_API WOLFSSL_X509_NAME* wolfSSL_sk_X509_NAME_pop(WOLF_STACK_OF(WOLFSSL_X509_NAME)*); +WOLFSSL_API void wolfSSL_sk_X509_NAME_pop_free(WOLF_STACK_OF(WOLFSSL_X509_NAME)*, + void f (WOLFSSL_X509_NAME*)); +WOLFSSL_API void wolfSSL_sk_X509_NAME_free(WOLF_STACK_OF(WOLFSSL_X509_NAME) *); + + WOLFSSL_API int wolfSSL_X509_NAME_print_ex(WOLFSSL_BIO*,WOLFSSL_X509_NAME*,int, unsigned long); @@ -3010,10 +3293,10 @@ WOLFSSL_API int wolfSSL_version(WOLFSSL*); WOLFSSL_API int wolfSSL_get_state(const WOLFSSL*); -WOLFSSL_API void* wolfSSL_sk_X509_NAME_value(const WOLF_STACK_OF(WOLFSSL_X509_NAME)*, int); - WOLFSSL_API void* wolfSSL_sk_X509_value(WOLF_STACK_OF(WOLFSSL_X509)*, int); +WOLFSSL_API void* wolfSSL_sk_X509_shift(WOLF_STACK_OF(WOLFSSL_X509)*); + WOLFSSL_API void* wolfSSL_SESSION_get_ex_data(const WOLFSSL_SESSION*, int); WOLFSSL_API int wolfSSL_SESSION_set_ex_data(WOLFSSL_SESSION*, int, void*); @@ -3027,6 +3310,8 @@ WOLFSSL_API int wolfSSL_X509_NAME_get_sz(WOLFSSL_X509_NAME*); WOLFSSL_API const unsigned char* wolfSSL_SESSION_get_id(WOLFSSL_SESSION*, unsigned int*); +WOLFSSL_API int wolfSSL_SESSION_print(WOLFSSL_BIO*, const WOLFSSL_SESSION*); + WOLFSSL_API int wolfSSL_set_tlsext_host_name(WOLFSSL *, const char *); WOLFSSL_API const char* wolfSSL_get_servername(WOLFSSL *, unsigned char); @@ -3042,7 +3327,7 @@ WOLFSSL_API void wolfSSL_CTX_set_servername_callback(WOLFSSL_CTX *, WOLFSSL_API int wolfSSL_CTX_set_tlsext_servername_callback(WOLFSSL_CTX *, CallbackSniRecv); -WOLFSSL_API void wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX *, void*); +WOLFSSL_API int wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX *, void*); WOLFSSL_API void wolfSSL_ERR_remove_thread_state(void*); @@ -3097,6 +3382,8 @@ WOLFSSL_API unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, const char **data, int *flags); WOLFSSL_API int wolfSSL_CTX_set_alpn_protos(WOLFSSL_CTX *ctx, const unsigned char *protos, unsigned int protos_len); +WOLFSSL_API int wolfSSL_set_alpn_protos(WOLFSSL* ssl, + const unsigned char* protos, unsigned int protos_len); WOLFSSL_API void *wolfSSL_OPENSSL_memdup(const void *data, size_t siz, const char* file, int line); WOLFSSL_API void wolfSSL_ERR_load_BIO_strings(void); @@ -3140,7 +3427,9 @@ WOLFSSL_API int wolfSSL_SSL_CTX_remove_session(WOLFSSL_CTX *, WOLFSSL_API WOLFSSL_BIO *wolfSSL_SSL_get_rbio(const WOLFSSL *s); WOLFSSL_API WOLFSSL_BIO *wolfSSL_SSL_get_wbio(const WOLFSSL *s); WOLFSSL_API int wolfSSL_SSL_do_handshake(WOLFSSL *s); -WOLFSSL_API int wolfSSL_SSL_in_init(WOLFSSL *a); /* #define in OpenSSL */ +WOLFSSL_API int wolfSSL_SSL_in_init(WOLFSSL*); +WOLFSSL_API int wolfSSL_SSL_in_connect_init(WOLFSSL*); + #ifndef NO_SESSION_CACHE WOLFSSL_API WOLFSSL_SESSION *wolfSSL_SSL_get0_session(const WOLFSSL *s); #endif @@ -3224,18 +3513,24 @@ WOLFSSL_API size_t SSL_get_peer_finished(const WOLFSSL *s, void *buf, size_t cou WOLFSSL_API int SSL_SESSION_set1_id(WOLFSSL_SESSION *s, const unsigned char *sid, unsigned int sid_len); WOLFSSL_API int SSL_SESSION_set1_id_context(WOLFSSL_SESSION *s, const unsigned char *sid_ctx, unsigned int sid_ctx_len); -WOLFSSL_API void *X509_get0_tbs_sigalg(const WOLFSSL_X509 *x); -WOLFSSL_API void X509_ALGOR_get0(WOLFSSL_ASN1_OBJECT **paobj, int *pptype, const void **ppval, const void *algor); -WOLFSSL_API void *X509_get_X509_PUBKEY(void * x); -WOLFSSL_API int X509_PUBKEY_get0_param(WOLFSSL_ASN1_OBJECT **ppkalg, const unsigned char **pk, int *ppklen, void **pa, WOLFSSL_EVP_PKEY *pub); +WOLFSSL_API const WOLFSSL_X509_ALGOR* wolfSSL_X509_get0_tbs_sigalg(const WOLFSSL_X509 *x); +WOLFSSL_API void wolfSSL_X509_ALGOR_get0(WOLFSSL_ASN1_OBJECT **paobj, int *pptype, const void **ppval, const WOLFSSL_X509_ALGOR *algor); +WOLFSSL_API WOLFSSL_X509_PUBKEY *wolfSSL_X509_get_X509_PUBKEY(const WOLFSSL_X509* x509); +WOLFSSL_API int wolfSSL_X509_PUBKEY_get0_param(WOLFSSL_ASN1_OBJECT **ppkalg, const unsigned char **pk, int *ppklen, void **pa, WOLFSSL_X509_PUBKEY *pub); WOLFSSL_API int i2t_ASN1_OBJECT(char *buf, int buf_len, WOLFSSL_ASN1_OBJECT *a); WOLFSSL_API int wolfSSL_i2a_ASN1_OBJECT(WOLFSSL_BIO *bp, WOLFSSL_ASN1_OBJECT *a); WOLFSSL_API void SSL_CTX_set_tmp_dh_callback(WOLFSSL_CTX *ctx, WOLFSSL_DH *(*dh) (WOLFSSL *ssl, int is_export, int keylength)); WOLFSSL_API WOLF_STACK_OF(SSL_COMP) *SSL_COMP_get_compression_methods(void); -WOLFSSL_API int X509_STORE_load_locations(WOLFSSL_X509_STORE *ctx, const char *file, const char *dir); +WOLFSSL_API int wolfSSL_X509_STORE_load_locations(WOLFSSL_X509_STORE *str, const char *file, const char *dir); WOLFSSL_API int wolfSSL_X509_STORE_add_crl(WOLFSSL_X509_STORE *ctx, WOLFSSL_X509_CRL *x); -WOLFSSL_API int wolfSSL_sk_SSL_CIPHER_num(const void * p); +WOLFSSL_API int wolfSSL_sk_SSL_CIPHER_num(const WOLF_STACK_OF(WOLFSSL_CIPHER)* p); +WOLFSSL_API int wolfSSL_sk_SSL_CIPHER_find( + WOLF_STACK_OF(WOLFSSL_CIPHER)* sk, const WOLFSSL_CIPHER* toFind); +WOLFSSL_API WOLF_STACK_OF(WOLFSSL_CIPHER)* wolfSSL_sk_SSL_CIPHER_dup( + WOLF_STACK_OF(WOLFSSL_CIPHER)* in); +WOLFSSL_API void wolfSSL_sk_SSL_CIPHER_free(WOLF_STACK_OF(WOLFSSL_CIPHER)* sk); WOLFSSL_API int wolfSSL_sk_SSL_COMP_zero(WOLFSSL_STACK* st); +WOLFSSL_API int wolfSSL_sk_SSL_COMP_num(WOLF_STACK_OF(WOLFSSL_COMP)* sk); WOLFSSL_API WOLFSSL_CIPHER* wolfSSL_sk_SSL_CIPHER_value(void *ciphers, int idx); WOLFSSL_API void ERR_load_SSL_strings(void); WOLFSSL_API void wolfSSL_EC_POINT_dump(const char *msg, const WOLFSSL_EC_POINT *p); diff --git a/wolfssl/wolfcrypt/asn.h b/wolfssl/wolfcrypt/asn.h index b5989d7f2..78427e957 100644 --- a/wolfssl/wolfcrypt/asn.h +++ b/wolfssl/wolfcrypt/asn.h @@ -144,6 +144,19 @@ enum DN_Tags { #define WOLFSSL_JOI_ST "/jurisdictionST=" #define WOLFSSL_EMAIL_ADDR "/emailAddress=" +#if defined(WOLFSSL_APACHE_HTTPD) + /* otherName strings */ + #define WOLFSSL_SN_MS_UPN "msUPN" + #define WOLFSSL_LN_MS_UPN "Microsoft Universal Principal Name" + #define WOLFSSL_MS_UPN_SUM 265 + #define WOLFSSL_SN_DNS_SRV "id-on-dnsSRV" + #define WOLFSSL_LN_DNS_SRV "SRVName otherName form" + /* TLS features extension strings */ + #define WOLFSSL_SN_TLS_FEATURE "tlsfeature" + #define WOLFSSL_LN_TLS_FEATURE "TLS Feature" + #define WOLFSSL_TLS_FEATURE_SUM 92 +#endif + /* NIDs */ enum { @@ -157,6 +170,10 @@ enum NID_id_pkix_OCSP_basic = 74, NID_any_policy = 75, NID_anyExtendedKeyUsage = 76, + NID_givenName = 99, + NID_initials = 101, + NID_title = 106, + NID_description = 107, NID_basic_constraints = 133, NID_key_usage = 129, /* 2.5.29.15 */ NID_ext_key_usage = 151, /* 2.5.29.37 */ @@ -173,8 +190,10 @@ enum NID_policy_mappings = 147, NID_policy_constraints = 150, NID_inhibit_any_policy = 168, /* 2.5.29.54 */ - NID_tlsfeature = 92, /* id-pe 24 */ + NID_tlsfeature = 1020, /* id-pe 24 */ NID_commonName = 0x03, /* matchs ASN_COMMON_NAME in asn.h */ + + NID_surname = 0x04, /* SN */ NID_serialNumber = 0x05, /* serialNumber */ NID_countryName = 0x06, /* C */ @@ -184,6 +203,8 @@ enum NID_organizationalUnitName = 0x0b, /* OU */ NID_domainComponent = 0x19, /* matchs ASN_DOMAIN_COMPONENT in asn.h */ NID_emailAddress = 0x30, /* emailAddress */ + NID_id_on_dnsSRV = 82, /* 1.3.6.1.5.5.7.8.7 */ + NID_ms_upn = 265 /* 1.3.6.1.4.1.311.20.2.3 */ }; enum ECC_TYPES @@ -197,12 +218,12 @@ enum ECC_TYPES ASN_PIV_CERT = 0x0A, ASN_PIV_NONCE = 0x0B, ASN_PIV_SIGNED_NONCE = 0x0C, - + ASN_PIV_TAG_CERT = 0x70, ASN_PIV_TAG_CERT_INFO = 0x71, ASN_PIV_TAG_MSCUID = 0x72, ASN_PIV_TAG_ERR_DET = 0xFE, - + /* certificate info masks */ ASN_PIV_CERT_INFO_COMPRESSED = 0x03, ASN_PIV_CERT_INFO_ISX509 = 0x04, @@ -341,6 +362,7 @@ enum Oid_Types { oidHmacType = 15, oidCompressType = 16, oidCertNameType = 17, + oidTlsExtType = 18, oidIgnoreType }; @@ -1229,6 +1251,9 @@ struct OcspRequest { byte issuerKeyHash[KEYID_SIZE]; byte* serial; /* copy of the serial number in source cert */ int serialSz; +#ifdef OPENSSL_EXTRA + WOLFSSL_ASN1_INTEGER* serialInt; +#endif byte* url; /* copy of the extAuthInfo in source cert */ int urlSz; diff --git a/wolfssl/wolfcrypt/asn_public.h b/wolfssl/wolfcrypt/asn_public.h index 9f5371e6d..9f2e62f0c 100644 --- a/wolfssl/wolfcrypt/asn_public.h +++ b/wolfssl/wolfcrypt/asn_public.h @@ -105,7 +105,8 @@ enum CertType { ED25519_TYPE, PKCS12_TYPE, PKCS8_PRIVATEKEY_TYPE, - PKCS8_ENC_PRIVATEKEY_TYPE + PKCS8_ENC_PRIVATEKEY_TYPE, + DETECT_CERT_TYPE }; @@ -192,6 +193,23 @@ typedef struct EncryptedInfo { } EncryptedInfo; +#define WOLFSSL_ASN1_INTEGER_MAX 20 +typedef struct WOLFSSL_ASN1_INTEGER { + /* size can be increased set at 20 for tag, length then to hold at least 16 + * byte type */ + unsigned char intData[WOLFSSL_ASN1_INTEGER_MAX]; + /* ASN_INTEGER | LENGTH | hex of number */ + unsigned char negative; /* negative number flag */ + + unsigned char* data; + unsigned int dataMax; /* max size of data buffer */ + unsigned int isDynamic:1; /* flag for if data pointer dynamic (1 is yes 0 is no) */ +#if defined(OPENSSL_ALL) || defined(WOLFSSL_QT) + int length; +#endif +} WOLFSSL_ASN1_INTEGER; + + #if defined(WOLFSSL_CERT_GEN) || defined(WOLFSSL_CERT_EXT) #ifdef WOLFSSL_EKU_OID #ifndef CTC_MAX_EKU_NB @@ -304,7 +322,6 @@ typedef struct Cert { } Cert; - /* Initialize and Set Certificate defaults: version = 3 (0x2) serial = 0 (Will be randomly generated) diff --git a/wolfssl/wolfcrypt/logging.h b/wolfssl/wolfcrypt/logging.h index ae2028c04..e776f2b43 100644 --- a/wolfssl/wolfcrypt/logging.h +++ b/wolfssl/wolfcrypt/logging.h @@ -163,9 +163,10 @@ WOLFSSL_API void wolfSSL_Debugging_OFF(void); #endif /* DEBUG_WOLFSSL && !WOLFSSL_DEBUG_ERRORS_ONLY */ -#if defined(DEBUG_WOLFSSL) || defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) || defined(WOLFSSL_HAPROXY) +#if defined(DEBUG_WOLFSSL) || defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX) ||\ + defined(WOLFSSL_HAPROXY) || defined(OPENSSL_EXTRA) - #if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) + #if (defined(OPENSSL_EXTRA) && !defined(_WIN32)) || defined(DEBUG_WOLFSSL_VERBOSE) WOLFSSL_API void WOLFSSL_ERROR_LINE(int err, const char* func, unsigned int line, const char* file, void* ctx); #define WOLFSSL_ERROR(x) \ diff --git a/wolfssl/wolfcrypt/memory.h b/wolfssl/wolfcrypt/memory.h index a2ed27b91..85c67ed65 100644 --- a/wolfssl/wolfcrypt/memory.h +++ b/wolfssl/wolfcrypt/memory.h @@ -105,7 +105,7 @@ WOLFSSL_API int wolfSSL_GetAllocators(wolfSSL_Malloc_cb*, #define WOLFMEM_BUCKETS 64,128,256,512,1024,2432,3456,4544,16128 #elif defined (OPENSSL_EXTRA) /* extra storage in structs for multiple attributes and order */ - #define WOLFMEM_BUCKETS 64,128,256,512,1024,2432,3360,4480,25520 + #define WOLFMEM_BUCKETS 64,128,256,512,1024,2432,3360,4480,25536 #elif defined (WOLFSSL_CERT_EXT) /* certificate extensions requires 24k for the SSL struct */ #define WOLFMEM_BUCKETS 64,128,256,512,1024,2432,3456,4544,24576 diff --git a/wolfssl/wolfcrypt/wc_port.h b/wolfssl/wolfcrypt/wc_port.h index c4a9eb37b..680e3a6d8 100644 --- a/wolfssl/wolfcrypt/wc_port.h +++ b/wolfssl/wolfcrypt/wc_port.h @@ -261,7 +261,7 @@ WOLFSSL_API int wc_FreeMutex(wolfSSL_Mutex*); WOLFSSL_API int wc_LockMutex(wolfSSL_Mutex*); WOLFSSL_API int wc_UnLockMutex(wolfSSL_Mutex*); #if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER) -/* dynamiclly set which mutex to use. unlock / lock is controlled by flag */ +/* dynamically set which mutex to use. unlock / lock is controlled by flag */ typedef void (mutex_cb)(int flag, int type, const char* file, int line); WOLFSSL_API int wc_LockMutex_ex(int flag, int type, const char* file, int line); diff --git a/wolfssl/wolfio.h b/wolfssl/wolfio.h index d1b97017a..c04176498 100644 --- a/wolfssl/wolfio.h +++ b/wolfssl/wolfio.h @@ -126,6 +126,7 @@ #include #endif #include + #define XFCNTL(fd, flag, block) fcntl((fd), (flag), (block)) #if defined(HAVE_RTP_SYS) #include