From b2b5d4e60376583b360e3f0bceefec5983dfaf8d Mon Sep 17 00:00:00 2001 From: Hideki Miyazaki Date: Wed, 28 Jul 2021 17:22:31 +0900 Subject: [PATCH 1/5] add evp_md_do_all --- tests/api.c | 50 +++++++++++++++++++++++++++++ wolfcrypt/src/evp.c | 73 ++++++++++++++++++++++++++++++++----------- wolfssl/openssl/evp.h | 5 +++ 3 files changed, 110 insertions(+), 18 deletions(-) diff --git a/tests/api.c b/tests/api.c index 8786331f5..1536ff510 100644 --- a/tests/api.c +++ b/tests/api.c @@ -46089,7 +46089,56 @@ static void test_EVP_blake2() AssertIntEQ(XSTRNCMP(md, "BLAKE2S256", XSTRLEN("BLAKE2S256")), 0); #endif printf(resultFmt, passed); +#endif +} + +#if defined(OPENSSL_EXTRA) +static void list_md_fn(const EVP_MD* m, const char* from, + const char* to, void* arg) +{ + const char* mn; + BIO *bio; + (void) from; + (void) to; + (void) arg; + (void) mn; + (void) bio; + + if (!m) { + /* alias */ + AssertNull(m); + AssertNotNull(to); + } + else { + AssertNotNull(m); + AssertNull(to); + } + AssertNotNull(from); + mn = EVP_get_digestbyname(from); + +#if !defined(NO_FILESYSTEM) && defined(DEBUG_WOLFSSL_VERBOSE) + /* print to stdout */ + AssertNotNull(arg); + + bio = BIO_new(BIO_s_file()); + BIO_set_fp(bio, arg, BIO_NOCLOSE); + BIO_printf(bio, "-%-14s to use the %s message digest algorithm\n", mn, mn); + BIO_free(bio); +#endif +} +#endif + +static void test_EVP_MD_do_all() +{ +#if defined(OPENSSL_EXTRA) + printf(testingFmt, "test_EVP_MD_do_all"); + + EVP_MD_do_all(list_md_fn, stdout); + /* to confirm previous call gives no harm */ + AssertTrue(1); + + printf(resultFmt, passed); #endif } /*----------------------------------------------------------------------------* @@ -46114,6 +46163,7 @@ void ApiTest(void) #endif test_wolfSSL_ERR_strings(); test_EVP_blake2(); + test_EVP_MD_do_all(); test_wolfSSL_CTX_use_certificate_file(); AssertIntEQ(test_wolfSSL_CTX_use_certificate_buffer(), WOLFSSL_SUCCESS); test_wolfSSL_CTX_use_PrivateKey_file(); diff --git a/wolfcrypt/src/evp.c b/wolfcrypt/src/evp.c index 91a895797..ffb54833d 100644 --- a/wolfcrypt/src/evp.c +++ b/wolfcrypt/src/evp.c @@ -3534,25 +3534,20 @@ int wolfSSL_EVP_Digest(const unsigned char* in, int inSz, unsigned char* out, return WOLFSSL_SUCCESS; } +static const struct alias { + const char *name; + const char *alias; +} alias_tbl[] = +{ + {"MD4", "ssl3-md4"}, + {"MD5", "ssl3-md5"}, + {"SHA1", "ssl3-sha1"}, + {"SHA1", "SHA"}, + { NULL, NULL} +}; + const WOLFSSL_EVP_MD *wolfSSL_EVP_get_digestbyname(const char *name) { - static const struct alias { - const char *name; - const char *alias; - } alias_tbl[] = - { - {"MD4", "ssl3-md4"}, - {"MD5", "ssl3-md5"}, - {"SHA1", "ssl3-sha1"}, - {"SHA1", "SHA"}, -#ifdef HAVE_BLAKE2 - {"BLAKE2b512", "blake2b512"}, -#endif -#ifdef HAVE_BLAKE2S - {"BLAKE2s256", "blake2s256"}, -#endif - { NULL, NULL} - }; char nameUpper[15]; /* 15 bytes should be enough for any name */ size_t i; @@ -3941,7 +3936,49 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } return (WOLFSSL_EVP_MD *)NULL; } - + + /* return alias name if has + * @param n message digest type name + * @return alias name, otherwise NULL + */ + static const char* hasAliasName(const char* n) + { + + const char* aliasnm = NULL; + const struct alias *al; + + for (al = alias_tbl; al->name != NULL; al++) + if(XSTRNCMP(n, al->name, XSTRLEN(al->name)+1) == 0) { + aliasnm = al->alias; + break; + } + + return aliasnm; + } + + /* do all md algorithm through a callback function + * @param fn a callback function to be called with all 'md' + * @param args arguments to pass to the callback + * @return none + */ + void wolfSSL_EVP_MD_do_all(void (*fn) (const WOLFSSL_EVP_MD *m, + const char* from, const char* to, void* xx), void* args) + { + const char* alias = NULL; + const struct s_ent *ent; + + /* loop all md */ + for (ent = md_tbl; ent->name != NULL; ent++){ + /* check if the md has alias */ + if((alias = hasAliasName(ent->name)) != NULL) { + fn(NULL, ent->name, ent->name, args); + } + else { + fn(ent->name, ent->name, NULL, args); + } + } + } + #ifndef NO_AES #ifdef HAVE_AES_CBC diff --git a/wolfssl/openssl/evp.h b/wolfssl/openssl/evp.h index 2cdf6fa8f..212bb6910 100644 --- a/wolfssl/openssl/evp.h +++ b/wolfssl/openssl/evp.h @@ -688,6 +688,10 @@ WOLFSSL_API int wolfSSL_PKCS5_PBKDF2_HMAC(const char *pass, int passlen, WOLFSSL_LOCAL int wolfSSL_EVP_get_hashinfo(const WOLFSSL_EVP_MD* evp, int* pHash, int* pHashSz); +WOLFSSL_API void wolfSSL_EVP_MD_do_all(void (*fn) (const WOLFSSL_EVP_MD *md, + const char* from, const char* to, + void* xx), void* args); + #define EVP_CIPH_STREAM_CIPHER WOLFSSL_EVP_CIPH_STREAM_CIPHER #define EVP_CIPH_ECB_MODE WOLFSSL_EVP_CIPH_ECB_MODE #define EVP_CIPH_CBC_MODE WOLFSSL_EVP_CIPH_CBC_MODE @@ -1016,6 +1020,7 @@ typedef WOLFSSL_ASN1_PCTX ASN1_PCTX; #define EVP_blake2b512 wolfSSL_EVP_blake2b512 #define EVP_blake2s256 wolfSSL_EVP_blake2s256 +#define EVP_MD_do_all wolfSSL_EVP_MD_do_all WOLFSSL_API void printPKEY(WOLFSSL_EVP_PKEY *k); From 2abf23cbc92f6eb875a0f0f9abd374277fd2826e Mon Sep 17 00:00:00 2001 From: Hideki Miyazaki Date: Thu, 29 Jul 2021 09:03:38 +0900 Subject: [PATCH 2/5] fix jenkins failure --- tests/api.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tests/api.c b/tests/api.c index 1536ff510..a75cdcb78 100644 --- a/tests/api.c +++ b/tests/api.c @@ -46114,10 +46114,11 @@ static void list_md_fn(const EVP_MD* m, const char* from, AssertNotNull(m); AssertNull(to); } + AssertNotNull(from); - mn = EVP_get_digestbyname(from); #if !defined(NO_FILESYSTEM) && defined(DEBUG_WOLFSSL_VERBOSE) + mn = EVP_get_digestbyname(from); /* print to stdout */ AssertNotNull(arg); From e333632ad07bee496d164239c00babce26044abd Mon Sep 17 00:00:00 2001 From: Hideki Miyazaki Date: Thu, 29 Jul 2021 14:37:10 +0900 Subject: [PATCH 3/5] add obj_name_do_all --- tests/api.c | 61 ++++++++++++++++++++++++++- wolfcrypt/src/evp.c | 87 +++++++++++++++++++++++++++++++++------ wolfssl/openssl/objects.h | 9 ++++ wolfssl/openssl/ssl.h | 1 + wolfssl/ssl.h | 17 ++++++++ 5 files changed, 162 insertions(+), 13 deletions(-) diff --git a/tests/api.c b/tests/api.c index a75cdcb78..8d3c88a2e 100644 --- a/tests/api.c +++ b/tests/api.c @@ -46124,7 +46124,7 @@ static void list_md_fn(const EVP_MD* m, const char* from, bio = BIO_new(BIO_s_file()); BIO_set_fp(bio, arg, BIO_NOCLOSE); - BIO_printf(bio, "-%-14s to use the %s message digest algorithm\n", mn, mn); + BIO_printf(bio, "Use %s message digest algorithm\n", mn); BIO_free(bio); #endif } @@ -46135,6 +46135,11 @@ static void test_EVP_MD_do_all() #if defined(OPENSSL_EXTRA) printf(testingFmt, "test_EVP_MD_do_all"); + EVP_MD_do_all(NULL, stdout); + /* to confirm previous call gives no harm */ + AssertTrue(1); + + EVP_MD_do_all(list_md_fn, stdout); /* to confirm previous call gives no harm */ AssertTrue(1); @@ -46142,6 +46147,59 @@ static void test_EVP_MD_do_all() printf(resultFmt, passed); #endif } + +#if defined(OPENSSL_EXTRA) +static void obj_name_t(const OBJ_NAME* nm, void* arg) +{ + (void)arg; + (void)nm; + + AssertIntGT(nm->type, OBJ_NAME_TYPE_UNDEF); + +#if !defined(NO_FILESYSTEM) && defined(DEBUG_WOLFSSL_VERBOSE) + /* print to stdout */ + AssertNotNull(arg); + + bio = BIO_new(BIO_s_file()); + BIO_set_fp(bio, arg, BIO_NOCLOSE); + BIO_printf(bio, "%s\n", mn); + BIO_free(bio); +#endif +} + +#endif +static void test_OBJ_NAME_do_all() +{ +#if defined(OPENSSL_EXTRA) + printf(testingFmt, "test_OBJ_NAME_do_all"); + + OBJ_NAME_do_all(OBJ_NAME_TYPE_MD_METH, NULL, NULL); + /* to confirm previous call gives no harm */ + AssertTrue(1); + + OBJ_NAME_do_all(OBJ_NAME_TYPE_CIPHER_METH, NULL, stdout); + /* to confirm previous call gives no harm */ + AssertTrue(1); + + OBJ_NAME_do_all(OBJ_NAME_TYPE_MD_METH, obj_name_t, stdout); + AssertTrue(1); + OBJ_NAME_do_all(OBJ_NAME_TYPE_PKEY_METH, obj_name_t, stdout); + AssertTrue(1); + OBJ_NAME_do_all(OBJ_NAME_TYPE_COMP_METH, obj_name_t, stdout); + AssertTrue(1); + OBJ_NAME_do_all(OBJ_NAME_TYPE_NUM, obj_name_t, stdout); + AssertTrue(1); + OBJ_NAME_do_all(OBJ_NAME_TYPE_UNDEF, obj_name_t, stdout); + AssertTrue(1); + OBJ_NAME_do_all(OBJ_NAME_TYPE_CIPHER_METH, obj_name_t, stdout); + AssertTrue(1); + OBJ_NAME_do_all(-1, obj_name_t, stdout); + AssertTrue(1); + + printf(resultFmt, passed); +#endif +} + /*----------------------------------------------------------------------------* | Main *----------------------------------------------------------------------------*/ @@ -46165,6 +46223,7 @@ void ApiTest(void) test_wolfSSL_ERR_strings(); test_EVP_blake2(); test_EVP_MD_do_all(); + test_OBJ_NAME_do_all(); test_wolfSSL_CTX_use_certificate_file(); AssertIntEQ(test_wolfSSL_CTX_use_certificate_buffer(), WOLFSSL_SUCCESS); test_wolfSSL_CTX_use_PrivateKey_file(); diff --git a/wolfcrypt/src/evp.c b/wolfcrypt/src/evp.c index ffb54833d..2558a1af9 100644 --- a/wolfcrypt/src/evp.c +++ b/wolfcrypt/src/evp.c @@ -3956,7 +3956,43 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) return aliasnm; } - /* do all md algorithm through a callback function + + struct do_all_md { + void *arg; + void (*fn) (const WOLFSSL_EVP_MD *m, + const char* from, const char* to, void *arg); + }; + + /* do all md algorithm + * @param nm a pointer to WOLFSSL_OBJ_NAME + * @param arg arguments to pass to the callback + * @return none + */ + static void md_do_all_func(const WOLFSSL_OBJ_NAME* nm, void* arg) + { + struct do_all_md *md = arg; + + const char* alias = NULL; + const struct s_ent *ent; + + /* sanity check */ + if (md == NULL || nm == NULL || md->fn == NULL || + nm->type != WOLFSSL_OBJ_NAME_TYPE_MD_METH) + return; + + /* loop all md */ + for (ent = md_tbl; ent->name != NULL; ent++){ + /* check if the md has alias */ + if((alias = hasAliasName(ent->name)) != NULL) { + md->fn(NULL, ent->name, ent->name, md->arg); + } + else { + md->fn(ent->name, ent->name, NULL, md->arg); + } + } + } + + /* call md_do_all function to do all md algorithm via a callback function * @param fn a callback function to be called with all 'md' * @param args arguments to pass to the callback * @return none @@ -3964,18 +4000,45 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) void wolfSSL_EVP_MD_do_all(void (*fn) (const WOLFSSL_EVP_MD *m, const char* from, const char* to, void* xx), void* args) { - const char* alias = NULL; - const struct s_ent *ent; + struct do_all_md md; - /* loop all md */ - for (ent = md_tbl; ent->name != NULL; ent++){ - /* check if the md has alias */ - if((alias = hasAliasName(ent->name)) != NULL) { - fn(NULL, ent->name, ent->name, args); - } - else { - fn(ent->name, ent->name, NULL, args); - } + md.fn = fn; + md.arg = args; + + return wolfSSL_OBJ_NAME_do_all(WOLFSSL_OBJ_NAME_TYPE_MD_METH, + md_do_all_func, &md); + } + + /* call "fn" based on OBJ_NAME type + * @param type OBJ_NAME type + * @param fn a callback function + * @param args arguments to pass to the callback + * @return none + */ + void wolfSSL_OBJ_NAME_do_all(int type, + void (*fn)(const WOLFSSL_OBJ_NAME*, void* arg), void* arg) + { + WOLFSSL_OBJ_NAME objnm; + + /* sanity check */ + if (!fn) + return; + + objnm.type = type; + + switch(type) { + case WOLFSSL_OBJ_NAME_TYPE_MD_METH: + fn(&objnm, arg); + break; + case WOLFSSL_OBJ_NAME_TYPE_CIPHER_METH: + case WOLFSSL_OBJ_NAME_TYPE_PKEY_METH: + case WOLFSSL_OBJ_NAME_TYPE_COMP_METH: + case WOLFSSL_OBJ_NAME_TYPE_NUM: + WOLFSSL_MSG("not implemented"); + FALL_THROUGH; + case WOLFSSL_OBJ_NAME_TYPE_UNDEF: + default: + break; } } diff --git a/wolfssl/openssl/objects.h b/wolfssl/openssl/objects.h index 3f975432b..ba79c48b4 100644 --- a/wolfssl/openssl/objects.h +++ b/wolfssl/openssl/objects.h @@ -34,6 +34,14 @@ extern "C" { #endif +#define OBJ_NAME_TYPE_UNDEF WOLFSSL_OBJ_NAME_TYPE_UNDEF +#define OBJ_NAME_TYPE_MD_METH WOLFSSL_OBJ_NAME_TYPE_MD_METH +#define OBJ_NAME_TYPE_CIPHER_METH WOLFSSL_OBJ_NAME_TYPE_CIPHER_METH +#define OBJ_NAME_TYPE_PKEY_METH WOLFSSL_OBJ_NAME_TYPE_PKEY_METH +#define OBJ_NAME_TYPE_COMP_METH WOLFSSL_OBJ_NAME_TYPE_COMP_METH +#define OBJ_NAME_TYPE_NUM WOLFSSL_OBJ_NAME_TYPE_NUM +#define OBJ_NAME_ALIAS WOLFSSL_OBJ_NAME_ALIAS + #define OBJ_nid2sn wolfSSL_OBJ_nid2sn #define OBJ_obj2nid wolfSSL_OBJ_obj2nid #define OBJ_sn2nid wolfSSL_OBJ_sn2nid @@ -47,6 +55,7 @@ #define OBJ_cmp wolfSSL_OBJ_cmp #define OBJ_create wolfSSL_OBJ_create #define ASN1_OBJECT_free wolfSSL_ASN1_OBJECT_free +#define OBJ_NAME_do_all wolfSSL_OBJ_NAME_do_all /* not required for wolfSSL */ #define OPENSSL_load_builtin_modules() diff --git a/wolfssl/openssl/ssl.h b/wolfssl/openssl/ssl.h index 2f1cbb4b9..3cd18295d 100644 --- a/wolfssl/openssl/ssl.h +++ b/wolfssl/openssl/ssl.h @@ -111,6 +111,7 @@ typedef WOLFSSL_dynlock_value CRYPTO_dynlock_value; typedef WOLFSSL_BUF_MEM BUF_MEM; typedef WOLFSSL_GENERAL_NAMES GENERAL_NAMES; typedef WOLFSSL_GENERAL_NAME GENERAL_NAME; +typedef WOLFSSL_OBJ_NAME OBJ_NAME; #define X509_L_FILE_LOAD WOLFSSL_X509_L_FILE_LOAD #define X509_L_ADD_DIR WOLFSSL_X509_L_ADD_DIR diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index b4f5daea8..2e13d0bc7 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -197,6 +197,7 @@ 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_v3_ext_method WOLFSSL_v3_ext_method; +typedef struct WOLFSSL_OBJ_NAME WOLFSSL_OBJ_NAME; typedef struct WOLFSSL_ASN1_STRING WOLFSSL_ASN1_STRING; typedef struct WOLFSSL_dynlock_value WOLFSSL_dynlock_value; @@ -217,6 +218,10 @@ typedef struct WOLFSSL_CONF_CTX WOLFSSL_CONF_CTX; #if defined(OPENSSL_ALL) || defined(OPENSSL_EXTRA) || defined(WOLFSSL_WPAS_SMALL) +struct WOLFSSL_OBJ_NAME { + int type; +}; + struct WOLFSSL_AUTHORITY_KEYID { WOLFSSL_ASN1_STRING *keyid; WOLFSSL_ASN1_OBJECT *issuer; @@ -3679,6 +3684,18 @@ WOLFSSL_API int wolfSSL_OBJ_create(const char *oid, const char *sn, const char * #ifdef HAVE_ECC WOLFSSL_LOCAL int NIDToEccEnum(int n); #endif + +#define WOLFSSL_OBJ_NAME_TYPE_UNDEF 0x00 +#define WOLFSSL_OBJ_NAME_TYPE_MD_METH 0x01 +#define WOLFSSL_OBJ_NAME_TYPE_CIPHER_METH 0x02 +#define WOLFSSL_OBJ_NAME_TYPE_PKEY_METH 0x03 +#define WOLFSSL_OBJ_NAME_TYPE_COMP_METH 0x04 +#define WOLFSSL_OBJ_NAME_TYPE_NUM 0x05 +#define WOLFSSL_OBJ_NAME_ALIAS 0x8000 + +WOLFSSL_API void wolfSSL_OBJ_NAME_do_all(int type, + void (*fn) (const WOLFSSL_OBJ_NAME* , void *arg), + void* arg); /* end of object functions */ WOLFSSL_API unsigned long wolfSSL_ERR_peek_last_error_line(const char **file, int *line); From 447705a2cbb9b47fa48d3838c023677295e1583c Mon Sep 17 00:00:00 2001 From: Hideki Miyazaki Date: Fri, 30 Jul 2021 10:21:16 +0900 Subject: [PATCH 4/5] fix jenkins failure --- wolfcrypt/src/evp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/src/evp.c b/wolfcrypt/src/evp.c index 2558a1af9..0b350dc7a 100644 --- a/wolfcrypt/src/evp.c +++ b/wolfcrypt/src/evp.c @@ -4005,7 +4005,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) md.fn = fn; md.arg = args; - return wolfSSL_OBJ_NAME_do_all(WOLFSSL_OBJ_NAME_TYPE_MD_METH, + wolfSSL_OBJ_NAME_do_all(WOLFSSL_OBJ_NAME_TYPE_MD_METH, md_do_all_func, &md); } From b27b4768ae1089b1fc5a12d1b35a74658eb8a95d Mon Sep 17 00:00:00 2001 From: Hideki Miyazaki Date: Sat, 31 Jul 2021 18:26:07 +0900 Subject: [PATCH 5/5] fix jenkins failure --- wolfcrypt/src/evp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/src/evp.c b/wolfcrypt/src/evp.c index 0b350dc7a..05cf734f0 100644 --- a/wolfcrypt/src/evp.c +++ b/wolfcrypt/src/evp.c @@ -3970,7 +3970,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) */ static void md_do_all_func(const WOLFSSL_OBJ_NAME* nm, void* arg) { - struct do_all_md *md = arg; + struct do_all_md *md = (struct do_all_md*)arg; const char* alias = NULL; const struct s_ent *ent;