Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -55,3 +55,4 @@ CLAUDE.md
/serial-file-test
/rand-file-test
manpages/*.1.gz
tests/x509/cert_setup_unit_test
1 change: 1 addition & 0 deletions Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ endif

include src/include.am
include wolfclu/include.am
include tests/x509/unit_include.am
if HAVE_PYTHON
include tests/dh/include.am
include tests/dsa/include.am
Expand Down
79 changes: 45 additions & 34 deletions src/crypto/clu_crypto_setup.c
Original file line number Diff line number Diff line change
Expand Up @@ -528,13 +528,52 @@ int wolfCLU_setup(int argc, char** argv, char action)
}
}

if (encCheck == 1 && decCheck == 1) {
WOLFCLU_LOG(WOLFCLU_E0,
"Encrypt and decrypt simultaneously is invalid");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}

if (inCheck == 0 && decCheck == 1) {
wolfCLU_LogError("File/string to decrypt needed");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}

if (ivCheck == 1) {
if (keyCheck == 0) {
WOLFCLU_LOG(WOLFCLU_E0,
"-iv was explicitly set, but no -key or -inkey was"
" provided. A non-password based key must be supplied"
" when setting the -iv flag.");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}
}

/* When the user supplies an explicit -key/-inkey, no salt-based
* key/iv derivation runs. The cipher therefore needs an explicit -iv:
* silently using the all-zero buffer would produce ciphertext that no
* one (including this tool on a later run) can decrypt safely. */
if (keyCheck == 1 && ivCheck == 0) {
WOLFCLU_LOG(WOLFCLU_E0,
"-key/-inkey requires -iv to be set: an IV must be"
" supplied alongside an explicit key.");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}

if (pwdKeyChk == 0 && keyCheck == 0) {
if (decCheck == 1) {
WOLFCLU_LOG(WOLFCLU_L0, "\nDECRYPT ERROR:");
wolfCLU_LogError("no key or passphrase set");
WOLFCLU_LOG(WOLFCLU_L0,
"Please type \"wolfssl -decrypt -help\" for decryption"
" usage \n");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
if (mode != NULL)
XFREE(mode, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
return WOLFCLU_FATAL_ERROR;
}
/* if no pwdKey is provided */
Expand All @@ -548,6 +587,12 @@ int wolfCLU_setup(int argc, char** argv, char action)
"No -pwd flag set, please enter a password to use for"
" encrypting.");
ret = wolfCLU_GetStdinPassword(pwdKey, &pwdBufSz);
if (ret != WOLFCLU_SUCCESS) {
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
if (mode != NULL)
XFREE(mode, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
return WOLFCLU_FATAL_ERROR;
}
pwdKeyChk = 1;
}
}
Expand All @@ -566,41 +611,7 @@ int wolfCLU_setup(int argc, char** argv, char action)
inCheck = 1;
}

if (encCheck == 1 && decCheck == 1) {
WOLFCLU_LOG(WOLFCLU_E0,
"Encrypt and decrypt simultaneously is invalid");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}

if (inCheck == 0 && decCheck == 1) {
wolfCLU_LogError("File/string to decrypt needed");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}

if (ivCheck == 1) {
if (keyCheck == 0) {
WOLFCLU_LOG(WOLFCLU_E0,
"-iv was explicitly set, but no -key or -inkey was"
" provided. A non-password based key must be supplied"
" when setting the -iv flag.");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}
}

/* When the user supplies an explicit -key/-inkey, no salt-based
* key/iv derivation runs. The cipher therefore needs an explicit -iv:
* silently using the all-zero buffer would produce ciphertext that no
* one (including this tool on a later run) can decrypt safely. */
if (keyCheck == 1 && ivCheck == 0) {
WOLFCLU_LOG(WOLFCLU_E0,
"-key/-inkey requires -iv to be set: an IV must be"
" supplied alongside an explicit key.");
wolfCLU_freeBins(pwdKey, iv, key, NULL, NULL);
return WOLFCLU_FATAL_ERROR;
}

if (pwdKeyChk == 1 && keyCheck == 1) {
XMEMSET(pwdKey, 0, keySize + block);
Expand Down
133 changes: 111 additions & 22 deletions src/genkey/clu_genkey.c
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,70 @@
#include <wolfclu/genkey/clu_genkey.h>
#include <wolfclu/x509/clu_parse.h>
#include <wolfclu/x509/clu_cert.h> /* PER_FORM/DER_FORM */
/* Opens path for writing owner-only, replacing any existing file. */
#ifdef _WIN32
#include <windows.h>
#include <sddl.h>
#include <io.h>
#include <fcntl.h>
#pragma comment(lib, "advapi32.lib")

static FILE* wolfCLU_OpenKeyFile(const char* path)
{
SECURITY_ATTRIBUTES sa;
PSECURITY_DESCRIPTOR pSD = NULL;
HANDLE hFile;
int fd;
FILE* f = NULL;
const char* sddl = "D:P(A;;FA;;;OW)";

(void)_unlink(path);
if (ConvertStringSecurityDescriptorToSecurityDescriptorA(sddl, SDDL_REVISION_1, &pSD, NULL)) {
sa.nLength = sizeof(SECURITY_ATTRIBUTES);
sa.bInheritHandle = FALSE;
sa.lpSecurityDescriptor = pSD;

hFile = CreateFileA(path, GENERIC_WRITE, 0, &sa, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
if (hFile != INVALID_HANDLE_VALUE) {
fd = _open_osfhandle((intptr_t)hFile, _O_WRONLY | _O_CREAT | _O_TRUNC);
if (fd != -1) {
f = _fdopen(fd, "wb");
}
if (f == NULL) {
if (fd != -1) _close(fd);
else CloseHandle(hFile);
(void)_unlink(path);
}
}
LocalFree(pSD);
}
return f;
}
#else
#include <fcntl.h>
#include <sys/stat.h>
#ifndef O_NOFOLLOW
#define O_NOFOLLOW 0
#endif
static FILE* wolfCLU_OpenKeyFile(const char* path)
{
int fd;
FILE* f;
/* Ignore the result (including ENOENT if the file doesn't exist yet);
* this just ensures the O_EXCL open below gets a fresh inode. */
(void)unlink(path);
fd = open(path, O_CREAT | O_EXCL | O_WRONLY | O_NOFOLLOW, 0600);
if (fd < 0)
return NULL;
f = fdopen(fd, "wb");
if (f == NULL) {
close(fd);
(void)unlink(path); /* remove the stray empty file we just created */
}
return f;
}
#endif /* _WIN32 */


#ifdef HAVE_ED25519
/* return WOLFCLU_SUCCESS on success */
Expand Down Expand Up @@ -121,7 +185,7 @@ int wolfCLU_genKey_ED25519(WC_RNG* rng, char* fOutNm, int directive, int format)

/* open the file for writing the private key */
if (ret == 0) {
file = XFOPEN(finalOutFNm, "wb");
file = wolfCLU_OpenKeyFile(finalOutFNm);
if (!file) {
ret = OUTPUT_FILE_ERROR;
}
Expand Down Expand Up @@ -663,11 +727,22 @@ int wolfCLU_GenAndOutput_ECC(WC_RNG* rng, char* fName, int directive,
fOutNameBuf[fNameSz + fExtSz] = '\0';
WOLFCLU_LOG(WOLFCLU_L0, "Private key file = %s", fOutNameBuf);

bioPri = wolfSSL_BIO_new_file(fOutNameBuf, "wb");
if (bioPri == NULL) {
wolfCLU_LogError("unable to read outfile %s",
fOutNameBuf);
ret = MEMORY_E;
{
FILE* f = wolfCLU_OpenKeyFile(fOutNameBuf);
if (f == NULL) {
wolfCLU_LogError("unable to read outfile %s",
fOutNameBuf);
ret = MEMORY_E;
}
else {
bioPri = wolfSSL_BIO_new_fp(f, BIO_CLOSE);
if (bioPri == NULL) {
XFCLOSE(f);
wolfCLU_LogError("unable to read outfile %s",
fOutNameBuf);
ret = MEMORY_E;
}
}
}
}

Expand Down Expand Up @@ -849,7 +924,7 @@ int wolfCLU_genKey_RSA(WC_RNG* rng, char* fName, int directive, int fmt, int

/* open the file for writing the private key */
if (ret == WOLFCLU_SUCCESS) {
file = XFOPEN(fOutNameBuf, "wb");
file = wolfCLU_OpenKeyFile(fOutNameBuf);
if (!file) {
ret = OUTPUT_FILE_ERROR;
}
Expand Down Expand Up @@ -1160,18 +1235,18 @@ int wolfCLU_genKey_Dilithium(WC_RNG* rng, char* fName, int directive, int fmt,
}
}

/* open file and write Private key */
/* open file and write Private key with owner-only perms */
if (ret == WOLFCLU_SUCCESS) {
file = XFOPEN(fOutNameBuf, "wb");
if (file == XBADFILE) {
file = wolfCLU_OpenKeyFile(fOutNameBuf);
if (file == NULL) {
wolfCLU_LogError("unable to open file %s",
fOutNameBuf);
ret = OUTPUT_FILE_ERROR;
}
}

if (ret == WOLFCLU_SUCCESS) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) <= 0) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) != outBufSz) {
ret = OUTPUT_FILE_ERROR;
}
}
Expand All @@ -1187,7 +1262,7 @@ int wolfCLU_genKey_Dilithium(WC_RNG* rng, char* fName, int directive, int fmt,
derBuf = NULL;
if (pemBuf != NULL) {
wolfCLU_ForceZero(pemBuf, pemBufSz);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_PRIVATE_KEY);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
pemBuf = NULL;
}

Expand Down Expand Up @@ -1238,7 +1313,7 @@ int wolfCLU_genKey_Dilithium(WC_RNG* rng, char* fName, int directive, int fmt,
}

if (ret == WOLFCLU_SUCCESS) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) <= 0) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) != outBufSz) {
ret = OUTPUT_FILE_ERROR;
}
}
Expand All @@ -1260,7 +1335,7 @@ int wolfCLU_genKey_Dilithium(WC_RNG* rng, char* fName, int directive, int fmt,

if (pemBuf != NULL) {
wolfCLU_ForceZero(pemBuf, pemBufSz);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_PRIVATE_KEY);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
}

if (fOutNameBuf != NULL) {
Expand Down Expand Up @@ -1408,18 +1483,18 @@ int wolfCLU_genKey_ML_DSA(WC_RNG* rng, char* fName, int directive, int fmt,
}
}

/* open file and write Private key */
/* open file and write Private key with owner-only perms */
if (ret == WOLFCLU_SUCCESS) {
file = XFOPEN(fOutNameBuf, "wb");
if (file == XBADFILE) {
file = wolfCLU_OpenKeyFile(fOutNameBuf);
if (file == NULL) {
wolfCLU_LogError("unable to open file %s",
fOutNameBuf);
ret = OUTPUT_FILE_ERROR;
}
}

if (ret == WOLFCLU_SUCCESS) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) <= 0) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) != outBufSz) {
ret = OUTPUT_FILE_ERROR;
}
}
Expand All @@ -1435,7 +1510,7 @@ int wolfCLU_genKey_ML_DSA(WC_RNG* rng, char* fName, int directive, int fmt,
derBuf = NULL;
if (pemBuf != NULL) {
wolfCLU_ForceZero(pemBuf, pemBufSz);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_PRIVATE_KEY);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
pemBuf = NULL;
}

Expand Down Expand Up @@ -1491,7 +1566,7 @@ int wolfCLU_genKey_ML_DSA(WC_RNG* rng, char* fName, int directive, int fmt,
}

if (ret == WOLFCLU_SUCCESS) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) <= 0) {
if ((int)XFWRITE(outBuf, 1, outBufSz, file) != outBufSz) {
ret = OUTPUT_FILE_ERROR;
}
}
Expand All @@ -1514,7 +1589,7 @@ int wolfCLU_genKey_ML_DSA(WC_RNG* rng, char* fName, int directive, int fmt,

if (pemBuf != NULL) {
wolfCLU_ForceZero(pemBuf, pemBufSz);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_PRIVATE_KEY);
XFREE(pemBuf, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
}

if (fOutNameBuf != NULL) {
Expand Down Expand Up @@ -1563,8 +1638,22 @@ enum wc_XmssRc wolfCLU_XmssKey_WriteCb(const byte * priv,
/* Open file for read and write. */
file = fopen(filename, "rb+");
if (!file) {
/* Create the file if it didn't exist. */
/* Create the file if it didn't exist. XMSS repeatedly reopens and
* updates this state file in place, so it can't go through
* wolfCLU_OpenKeyFile's O_EXCL create-and-replace pattern; lock
* down permissions right after creation instead. */
#ifndef _WIN32
{
int fd = open(filename, O_CREAT | O_EXCL | O_RDWR | O_NOFOLLOW, 0600);
if (fd >= 0) {
file = fdopen(fd, "wb+");
if (!file)
close(fd);
}
}
#else
file = fopen(filename, "wb+");
Comment thread
stenslae marked this conversation as resolved.
#endif
if (!file) {
fprintf(stderr, "error: fopen(%s, \"w+\") failed.\n", filename);
return WC_XMSS_RC_WRITE_FAIL;
Expand Down
6 changes: 3 additions & 3 deletions src/ocsp/clu_ocsp.c
Original file line number Diff line number Diff line change
Expand Up @@ -858,10 +858,10 @@ static int ocspResponder(OcspResponderConfig* config)
if (transportSendResponse(clientfd, transportType, respBuffer, (int)respSz) != 0)
goto continue_loop;

/* Count only successful OCSP requests (not OCSP-level errors like
* malformed requests) to prevent a single bad client from easily
* exhausting the -nrequest budget. */
if (ocspStatus == OCSP_SUCCESSFUL) {
/* Only count successfully processed requests toward the -nrequest
* limit. Failed reads/sends jump to continue_loop above, so a
* misbehaving client cannot exhaust the budget. */
requestsProcessed++;
}

Expand Down
Loading
Loading