From 45a13e1491a52cc2777556156ce4383dbbe35e47 Mon Sep 17 00:00:00 2001 From: David Garske Date: Wed, 23 Feb 2022 15:59:17 -0800 Subject: [PATCH] Improvements based on peer review. Added section in README.md. --- certgen/README.md | 81 ++++++++++ certgen/csr_cryptocb.c | 310 +++++++++++++++++++----------------- tls/client-tls-pkcallback.c | 2 +- 3 files changed, 245 insertions(+), 148 deletions(-) diff --git a/certgen/README.md b/certgen/README.md index 3331ecbe..4322fc3a 100644 --- a/certgen/README.md +++ b/certgen/README.md @@ -252,3 +252,84 @@ bmQHbpv7R5cK0GP2bFkqggIgN1wA6w19lVFdjukGx6VvfYsdaY2O+Fu6Ew4qX7SG GxI= -----END CERTIFICATE----- ``` + + +## Certificate Signing Request (CSR) Example with Crypto Callbacks + +Example of generating a PEM-encoded certificate signing request (CSR) using the +Crypto Callbacks to show signing against HSM/TPM + +Tested with these wolfSSL build options: + +``` +./configure --enable-certreq --enable-certgen --enable-certext --enable-cryptocb +make +sudo make install +``` + +### `csr_cryptocb` Example output + +``` +% ./csr_cryptocb +Invalid input supplied try one of the below examples +Examples: + +./csr_cryptocb rsa +./csr_cryptocb ecc +./csr_cryptocb ed25519 +``` + +``` +% ./csr_cryptocb ecc +CryptoCb: PK ECDSA-Sign (4) +-----BEGIN CERTIFICATE REQUEST----- +MIIBTDCB8wIBAjCBkDELMAkGA1UEBhMCVVMxCzAJBgNVBAgMAk9SMREwDwYDVQQH +DAhQb3J0bGFuZDEQMA4GA1UECgwHd29sZlNTTDEUMBIGA1UECwwLRGV2ZWxvcG1l +bnQxGDAWBgNVBAMMD3d3dy53b2xmc3NsLmNvbTEfMB0GCSqGSIb3DQEJARYQaW5m +b0B3b2xmc3NsLmNvbTBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABLszrEwnUErG +SqUEwzzenzbbci3OlOor+ssgCTksFuhhAumvTdMCk5oxW5eSIX/wzxjakRECNIbo +IFgzC4A0idigADAKBggqhkjOPQQDAgNIADBFAiEAmJK6ZapcFw4NTjImNoBrpudZ +6sFvRccABG35QyASvIsCIFXcN4Wo5qiH37OjT7dehbdZvQbJFw4hKOtim1gw5Z4p +-----END CERTIFICATE REQUEST----- + (525) +Saved CSR PEM to "ecc-csr.pem" + +``` +% ./csr_cryptocb rsa +CryptoCb: PK RSA (1) +-----BEGIN CERTIFICATE REQUEST----- +MIIC1jCCAb4CAQIwgZAxCzAJBgNVBAYTAlVTMQswCQYDVQQIDAJPUjERMA8GA1UE +BwwIUG9ydGxhbmQxEDAOBgNVBAoMB3dvbGZTU0wxFDASBgNVBAsMC0RldmVsb3Bt +ZW50MRgwFgYDVQQDDA93d3cud29sZnNzbC5jb20xHzAdBgkqhkiG9w0BCQEWEGlu +Zm9Ad29sZnNzbC5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDD +A9Er/jmkMkU7U8iEKyp8dJq9qipSB0fWpjayBzKO0Lppe8bDRJ7UgUj9LWiii2e7 +oXXINixK0hv3i7rPDfnv7PGBHnubA0eav2XMf2UkaaboFIlb5DT3xbAUk/Vnezp6 +eOEBVlaRphNCjdI8QJxM79GG3zdRGwyhO/Xxo0o15OHOlt8bfr9Ol9AQ6KgIMIGv +IAtDFMV0Z7Qygm+NhsKIQJk2g7oeQHIiF9dSZSRzsM7vGc2u/3hse8ASA9ROcg1Q +bTujO6OZXp3I2QyFs9mK2VQm2236rLv/JUzE0Xn0cdOGQBgTsGO1ck4wxJeEhi1W +L9cV93/ArvX8W+X7obrTAgMBAAGgADANBgkqhkiG9w0BAQsFAAOCAQEAK+RxSIQ4 +CqxYbicHcbFZgHrTy7MOoA8uM5XWIP/AKZ4u64zbF2K6XIMItrfIGEouc6MDfKVh +W8ml6O75SR/7h/8S/9GClqcuzFqtNflzmb20Oadkl09sRIXPhFXMpt4V+Zc4cOka +kcqL0q+oEU+8naRJJ6pa6LL1NWRq79es4DykvtHcGkx0J1VPlu3ux7iYlQ0fVfRs +QUI1z3K52qfuchKW5zwkDjkVDbiWPd0/pbtUW2f8TAC21h0NabwMGISrrxmu6SX2 +wI8YHCyLX5sMUosQ78vuGBD0bD5rxil0lzO9pjvWiSLZe0ubJ2Qq+FiuqIqITRiy +5AMQEs5siVCCEA== +-----END CERTIFICATE REQUEST----- + (1062) +Saved CSR PEM to "rsa-csr.pem" +``` + +``` +% ./csr_cryptocb ed25519 +CryptoCb: PK ED25519-Sign (6) +-----BEGIN CERTIFICATE REQUEST----- +MIIBETCBxAIBAjCBkDELMAkGA1UEBhMCVVMxCzAJBgNVBAgMAk9SMREwDwYDVQQH +DAhQb3J0bGFuZDEQMA4GA1UECgwHd29sZlNTTDEUMBIGA1UECwwLRGV2ZWxvcG1l +bnQxGDAWBgNVBAMMD3d3dy53b2xmc3NsLmNvbTEfMB0GCSqGSIb3DQEJARYQaW5m +b0B3b2xmc3NsLmNvbTAqMAUGAytlcAMhAOZXWxMbx1EUa+079dH6q55stusCCaOZ +9W6/nTz+VDnmoAAwBQYDK2VwA0EAZX+pExcyCYxJHJmmISW8AxfhgJ/PmTPK4+uH +7iTt+VTNvi/Z6IPjlg+UWIbyyCno0RoNnB7GiqnvPn8fVAcsAw== +-----END CERTIFICATE REQUEST----- + (448) +Saved CSR PEM to "ed25519-csr.pem" +``` diff --git a/certgen/csr_cryptocb.c b/certgen/csr_cryptocb.c index 2a5fa3f0..87d1ae6c 100644 --- a/certgen/csr_cryptocb.c +++ b/certgen/csr_cryptocb.c @@ -19,7 +19,8 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA */ -/* Example of generating a PEM-encoded certificate signing request (CSR). */ +/* Example of generating a PEM-encoded certificate signing request (CSR) using + * the Crypto Callbacks to show signing against HSM/TPM */ #ifndef WOLFSSL_USER_SETTINGS #include @@ -37,8 +38,13 @@ #define DEBUG_CRYPTOCB #if defined(WOLF_CRYPTO_CB) && defined(WOLFSSL_CERT_REQ) && \ - defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_CERT_GEN) + defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_CERT_GEN) && \ + (!defined(NO_RSA) || defined(HAVE_ECC) || defined(HAVE_ED25519)) +#define ENABLE_CSR_EXAMPLE +#endif + +#ifdef ENABLE_CSR_EXAMPLE static void usage(void) { printf("Invalid input supplied try one of the below examples\n"); @@ -54,143 +60,12 @@ typedef struct { const char* keyFilePriv; } myCryptoCbCtx; -#ifdef DEBUG_CRYPTOCB -static const char* GetAlgoTypeStr(int algo) -{ - switch (algo) { /* enum wc_AlgoType */ - case WC_ALGO_TYPE_HASH: return "Hash"; - case WC_ALGO_TYPE_CIPHER: return "Cipher"; - case WC_ALGO_TYPE_PK: return "PK"; - case WC_ALGO_TYPE_RNG: return "RNG"; - case WC_ALGO_TYPE_SEED: return "Seed"; - case WC_ALGO_TYPE_HMAC: return "HMAC"; - } - return NULL; -} -static const char* GetPkTypeStr(int pk) -{ - switch (pk) { - case WC_PK_TYPE_RSA: return "RSA"; - case WC_PK_TYPE_DH: return "DH"; - case WC_PK_TYPE_ECDH: return "ECDH"; - case WC_PK_TYPE_ECDSA_SIGN: return "ECDSA-Sign"; - case WC_PK_TYPE_ECDSA_VERIFY: return "ECDSA-Verify"; - case WC_PK_TYPE_ED25519_SIGN: return "ED25519-Sign"; - case WC_PK_TYPE_ED25519_VERIFY: return "ED25519-Verify"; - case WC_PK_TYPE_CURVE25519: return "CURVE25519"; - case WC_PK_TYPE_RSA_KEYGEN: return "RSA KeyGen"; - case WC_PK_TYPE_EC_KEYGEN: return "ECC KeyGen"; - } - return NULL; -} -#endif /* DEBUG_CRYPTOCB */ - -/* reads file size, allocates buffer, reads into buffer, returns buffer */ -static int load_file(const char* fname, byte** buf, size_t* bufLen) -{ - int ret; - long int fileSz; - XFILE lFile; - - if (fname == NULL || buf == NULL || bufLen == NULL) - return BAD_FUNC_ARG; - - /* set defaults */ - *buf = NULL; - *bufLen = 0; - - /* open file (read-only binary) */ - lFile = XFOPEN(fname, "rb"); - if (!lFile) { - printf("Error loading %s\n", fname); - return BAD_PATH_ERROR; - } - - fseek(lFile, 0, SEEK_END); - fileSz = (int)ftell(lFile); - rewind(lFile); - if (fileSz > 0) { - *bufLen = (size_t)fileSz; - *buf = (byte*)malloc(*bufLen); - if (*buf == NULL) { - ret = MEMORY_E; - printf("Error allocating %lu bytes\n", (unsigned long)*bufLen); - } - else { - size_t readLen = fread(*buf, *bufLen, 1, lFile); - - /* check response code */ - ret = (readLen > 0) ? 0 : -1; - } - } - else { - ret = BUFFER_E; - } - fclose(lFile); - - return ret; -} - +/* Forward declarations */ static int load_key_file(const char* fname, byte* derBuf, word32* derLen, - int isPubKey) -{ - int ret; - byte* buf = NULL; - size_t bufLen; - - ret = load_file(fname, &buf, &bufLen); - if (ret != 0) - return ret; - - if (isPubKey) { - ret = wc_PubKeyPemToDer(buf, (word32)bufLen, derBuf, (word32)bufLen); - } else { - ret = wc_KeyPemToDer(buf, (word32)bufLen, derBuf, (word32)bufLen, NULL); - } - if (ret < 0) { - free(buf); - return ret; - } - *derLen = ret; - free(buf); - - return 0; -} - -#ifdef WOLFSSL_DER_TO_PEM -static int save_der_as_pem(const byte* der, word32 derSz, const char* arg1, - int type) -{ - int ret; - byte pem[LARGE_TEMP_SZ]; - int pemSz; - FILE* file = NULL; - char outFile[255]; - - memset(pem, 0, sizeof(pem)); - ret = wc_DerToPem(der, derSz, pem, sizeof(pem), type); - if (ret <= 0) { - printf("CSR DER to PEM failed: %d\n", ret); - return ret; - } - pemSz = ret; - printf("%s (%d)\n", pem, pemSz); - - snprintf(outFile, sizeof(outFile), "%s-csr.pem", arg1); - printf("Saved CSR PEM to \"%s\"\n", outFile); - file = fopen(outFile, "wb"); - if (file) { - ret = (int)fwrite(pem, 1, pemSz, file); - if (ret == pemSz) { - ret = 0; - } - fclose(file); - } - else { - ret = -1; - } - return ret; -} + int isPubKey); +#ifdef DEBUG_CRYPTOCB +static const char* GetAlgoTypeStr(int algo); +static const char* GetPkTypeStr(int pk); #endif /* Example crypto dev callback function that calls software version */ @@ -214,7 +89,7 @@ static int myCryptoDevCb(int devIdArg, wc_CryptoInfo* info, void* ctx) if (info->algo_type == WC_ALGO_TYPE_PK) { #ifdef DEBUG_CRYPTOCB - printf("CryptoCb: %s %s (%d)\n", GetAlgoTypeStr(info->algo_type), + printf("CryptoCb: %s %s (%d)\n", GetAlgoTypeStr(info->algo_type), GetPkTypeStr(info->pk.type), info->pk.type); #endif @@ -300,6 +175,146 @@ static int myCryptoDevCb(int devIdArg, wc_CryptoInfo* info, void* ctx) return ret; } + +#ifdef DEBUG_CRYPTOCB +static const char* GetAlgoTypeStr(int algo) +{ + switch (algo) { /* enum wc_AlgoType */ + case WC_ALGO_TYPE_HASH: return "Hash"; + case WC_ALGO_TYPE_CIPHER: return "Cipher"; + case WC_ALGO_TYPE_PK: return "PK"; + case WC_ALGO_TYPE_RNG: return "RNG"; + case WC_ALGO_TYPE_SEED: return "Seed"; + case WC_ALGO_TYPE_HMAC: return "HMAC"; + } + return NULL; +} +static const char* GetPkTypeStr(int pk) +{ + switch (pk) { + case WC_PK_TYPE_RSA: return "RSA"; + case WC_PK_TYPE_DH: return "DH"; + case WC_PK_TYPE_ECDH: return "ECDH"; + case WC_PK_TYPE_ECDSA_SIGN: return "ECDSA-Sign"; + case WC_PK_TYPE_ECDSA_VERIFY: return "ECDSA-Verify"; + case WC_PK_TYPE_ED25519_SIGN: return "ED25519-Sign"; + case WC_PK_TYPE_ED25519_VERIFY: return "ED25519-Verify"; + case WC_PK_TYPE_CURVE25519: return "CURVE25519"; + case WC_PK_TYPE_RSA_KEYGEN: return "RSA KeyGen"; + case WC_PK_TYPE_EC_KEYGEN: return "ECC KeyGen"; + } + return NULL; +} +#endif /* DEBUG_CRYPTOCB */ + +/* reads file size, allocates buffer, reads into buffer, returns buffer */ +static int load_file(const char* fname, byte** buf, size_t* bufLen) +{ + int ret; + long int fileSz; + XFILE lFile; + + if (fname == NULL || buf == NULL || bufLen == NULL) + return BAD_FUNC_ARG; + + /* set defaults */ + *buf = NULL; + *bufLen = 0; + + /* open file (read-only binary) */ + lFile = XFOPEN(fname, "rb"); + if (!lFile) { + printf("Error loading %s\n", fname); + return BAD_PATH_ERROR; + } + + fseek(lFile, 0, SEEK_END); + fileSz = (int)ftell(lFile); + rewind(lFile); + if (fileSz > 0) { + *bufLen = (size_t)fileSz; + *buf = (byte*)malloc(*bufLen); + if (*buf == NULL) { + ret = MEMORY_E; + printf("Error allocating %lu bytes\n", (unsigned long)*bufLen); + } + else { + size_t readLen = fread(*buf, *bufLen, 1, lFile); + + /* check response code */ + ret = (readLen > 0) ? 0 : -1; + } + } + else { + ret = BUFFER_E; + } + fclose(lFile); + + return ret; +} + +static int load_key_file(const char* fname, byte* derBuf, word32* derLen, + int isPubKey) +{ + int ret; + byte* buf = NULL; + size_t bufLen; + + ret = load_file(fname, &buf, &bufLen); + if (ret != 0) + return ret; + + if (isPubKey) { + ret = wc_PubKeyPemToDer(buf, (word32)bufLen, derBuf, (word32)bufLen); + } else { + ret = wc_KeyPemToDer(buf, (word32)bufLen, derBuf, (word32)bufLen, NULL); + } + if (ret < 0) { + free(buf); + return ret; + } + *derLen = ret; + free(buf); + + return 0; +} + +#ifdef WOLFSSL_DER_TO_PEM +static int save_der_as_pem(const byte* der, word32 derSz, const char* arg1, + int type) +{ + int ret; + byte pem[LARGE_TEMP_SZ]; + int pemSz; + FILE* file = NULL; + char outFile[255]; + + memset(pem, 0, sizeof(pem)); + ret = wc_DerToPem(der, derSz, pem, sizeof(pem), type); + if (ret <= 0) { + printf("CSR DER to PEM failed: %d\n", ret); + return ret; + } + pemSz = ret; + printf("%s (%d)\n", pem, pemSz); + + snprintf(outFile, sizeof(outFile), "%s-csr.pem", arg1); + printf("Saved CSR PEM to \"%s\"\n", outFile); + file = fopen(outFile, "wb"); + if (file) { + ret = (int)fwrite(pem, 1, pemSz, file); + if (ret == pemSz) { + ret = 0; + } + fclose(file); + } + else { + ret = -1; + } + return ret; +} +#endif + static int gen_csr(const char* arg1) { int ret; @@ -328,8 +343,10 @@ static int gen_csr(const char* arg1) type = ECC_TYPE; else if (XSTRNCMP(arg1, "ed25519", 7) == 0) type = ED25519_TYPE; - else + else { + printf("Invalid argument or not compiled in (expect: rsa, ecc or ed25519)\n"); return NOT_COMPILED_IN; + } wolfCrypt_Init(); @@ -465,7 +482,7 @@ static int gen_csr(const char* arg1) #endif ret = 0; /* success */ - + exit: #ifdef HAVE_ECC if (type == ECC_TYPE) @@ -486,20 +503,19 @@ exit: return ret; } -#endif +#endif int main(int argc, char** argv) { -#if !defined(WOLF_CRYPTO_CB) || !defined(WOLFSSL_CERT_REQ) || \ - !defined(WOLFSSL_CERT_EXT) || !defined(WOLFSSL_CERT_GEN) - printf("Please compile wolfSSL with --enable-certreq --enable-certgen --enable-certext --enable-cryptocb\n"); - return 0; -#else +#ifdef ENABLE_CSR_EXAMPLE if (argc != 2) { usage(); return 1; } return gen_csr(argv[1]); +#else + printf("Please compile wolfSSL with --enable-certreq --enable-certgen --enable-certext --enable-cryptocb\n"); + return 0; #endif } diff --git a/tls/client-tls-pkcallback.c b/tls/client-tls-pkcallback.c index e08d2e6f..26d855d4 100644 --- a/tls/client-tls-pkcallback.c +++ b/tls/client-tls-pkcallback.c @@ -87,7 +87,7 @@ static int load_file(const char* fname, byte** buf, size_t* bufLen) fseek(lFile, 0, SEEK_END); fileSz = (int)ftell(lFile); rewind(lFile); - if (fileSz > 0) { + if (fileSz > 0) { *bufLen = (size_t)fileSz; *buf = (byte*)malloc(*bufLen); if (*buf == NULL) {