summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/freebl/blapii.h10
-rw-r--r--lib/freebl/drbg.c6
-rw-r--r--lib/freebl/dsa.c12
-rw-r--r--lib/freebl/ec.c10
-rw-r--r--lib/freebl/ecl/ecp_jm.c5
-rw-r--r--lib/freebl/gcm.c16
-rw-r--r--lib/freebl/hmacct.c5
-rw-r--r--lib/freebl/mpi/mpmontg.c6
-rw-r--r--lib/freebl/pqg.c45
-rw-r--r--lib/freebl/rijndael.c24
-rw-r--r--lib/freebl/rsa.c2
-rw-r--r--lib/freebl/rsapkcs.c8
-rw-r--r--lib/freebl/shvfy.c13
-rw-r--r--lib/freebl/unix_urandom.c1
-rw-r--r--lib/softoken/fipstokn.c6
-rw-r--r--lib/softoken/lowkey.c8
-rw-r--r--lib/softoken/lowpbe.c39
-rw-r--r--lib/softoken/pkcs11.c21
-rw-r--r--lib/softoken/pkcs11c.c467
-rw-r--r--lib/softoken/pkcs11i.h33
-rw-r--r--lib/softoken/pkcs11u.c21
-rw-r--r--lib/softoken/sftkdb.c33
-rw-r--r--lib/softoken/sftkhmac.c6
-rw-r--r--lib/softoken/sftkike.c4
-rw-r--r--lib/softoken/sftkpwd.c15
-rw-r--r--lib/softoken/tlsprf.c2
-rw-r--r--lib/util/secalgid.c2
-rw-r--r--lib/util/secdig.c2
28 files changed, 466 insertions, 356 deletions
diff --git a/lib/freebl/blapii.h b/lib/freebl/blapii.h
index e3177097f..7db57cdb0 100644
--- a/lib/freebl/blapii.h
+++ b/lib/freebl/blapii.h
@@ -98,4 +98,14 @@ PRBool arm_sha1_support();
PRBool arm_sha2_support();
PRBool ppc_crypto_support();
+#ifdef NSS_FIPS_DISABLED
+#define BLAPI_CLEAR_STACK(stack_size)
+#else
+#define BLAPI_CLEAR_STACK(stack_size) \
+ { \
+ volatile char _stkclr[stack_size]; \
+ PORT_Memset((void *)&_stkclr[0], 0, stack_size); \
+ }
+#endif
+
#endif /* _BLAPII_H_ */
diff --git a/lib/freebl/drbg.c b/lib/freebl/drbg.c
index 85e9e61b6..3ed1751c3 100644
--- a/lib/freebl/drbg.c
+++ b/lib/freebl/drbg.c
@@ -145,6 +145,7 @@ prng_Hash_df(PRUint8 *requested_bytes, unsigned int no_of_bytes_to_return,
requested_bytes += hash_return_len;
no_of_bytes_to_return -= hash_return_len;
}
+ SHA256_DestroyContext(&ctx, PR_FALSE);
return SECSuccess;
}
@@ -197,6 +198,7 @@ prng_initEntropy(void)
SHA256_End(&ctx, globalrng->previousEntropyHash, NULL,
sizeof(globalrng->previousEntropyHash));
PORT_Memset(block, 0, sizeof(block));
+ SHA256_DestroyContext(&ctx, PR_FALSE);
return PR_SUCCESS;
}
@@ -244,6 +246,7 @@ prng_getEntropy(PRUint8 *buffer, size_t requestLength)
}
out:
+ PORT_Memset(hash, 0, sizeof hash);
PORT_Memset(block, 0, sizeof block);
return rv;
}
@@ -388,6 +391,7 @@ prng_Hashgen(RNGContext *rng, PRUint8 *returned_bytes,
* This increments data if no_of_returned_bytes is not zero */
carry = no_of_returned_bytes;
PRNG_ADD_CARRY_ONLY(data, (sizeof data) - 1, carry);
+ SHA256_DestroyContext(&ctx, PR_FALSE);
}
PORT_Memset(data, 0, sizeof data);
PORT_Memset(thisHash, 0, sizeof thisHash);
@@ -430,6 +434,7 @@ prng_generateNewBytes(RNGContext *rng,
SHA256_End(&ctx, w, NULL, sizeof w);
PRNG_ADD_BITS_AND_CARRY(V(rng), VSize(rng), w, sizeof w, carry)
PORT_Memset(w, 0, sizeof w);
+ SHA256_DestroyContext(&ctx, PR_FALSE);
#undef w
}
@@ -450,6 +455,7 @@ prng_generateNewBytes(RNGContext *rng,
PRNG_ADD_CARRY_ONLY(rng->reseed_counter, (sizeof rng->reseed_counter) - 1, carry);
/* if the prng failed, don't return any output, signal softoken */
+ PORT_Memset(H, 0, sizeof H);
if (!rng->isValid) {
PORT_Memset(returned_bytes, 0, no_of_returned_bytes);
PORT_SetError(SEC_ERROR_LIBRARY_FAILURE);
diff --git a/lib/freebl/dsa.c b/lib/freebl/dsa.c
index 389c9de24..b81d9a370 100644
--- a/lib/freebl/dsa.c
+++ b/lib/freebl/dsa.c
@@ -260,7 +260,7 @@ DSA_NewRandom(PLArenaPool *arena, const SECItem *q, SECItem *seed)
PORT_SetError(SEC_ERROR_NEED_RANDOM);
loser:
if (arena != NULL) {
- SECITEM_FreeItem(seed, PR_FALSE);
+ SECITEM_ZfreeItem(seed, PR_FALSE);
}
return SECFailure;
}
@@ -295,7 +295,7 @@ DSA_NewKey(const PQGParams *params, DSAPrivateKey **privKey)
rv = dsa_NewKeyExtended(params, &seed, privKey);
}
}
- SECITEM_FreeItem(&seed, PR_FALSE);
+ SECITEM_ZfreeItem(&seed, PR_FALSE);
return rv;
}
@@ -403,6 +403,8 @@ dsa_SignDigest(DSAPrivateKey *key, SECItem *signature, const SECItem *digest,
CHECK_MPI_OK(mp_exptmod(&g, &t, &p, &r)); /* r = g**t mod p */
/* r is now g**(k+q*fuzz) == g**k mod p */
CHECK_MPI_OK(mp_mod(&r, &q, &r)); /* r = r mod q */
+ /* make sure fuzz is cleared off the stack and not optimized away */
+ *(volatile mp_digit *)&fuzz = 0;
/*
** FIPS 186-1, Section 5, Step 2
@@ -415,14 +417,14 @@ dsa_SignDigest(DSAPrivateKey *key, SECItem *signature, const SECItem *digest,
goto cleanup;
}
SECITEM_TO_MPINT(t2, &t); /* t <-$ Zq */
- SECITEM_FreeItem(&t2, PR_FALSE);
+ SECITEM_ZfreeItem(&t2, PR_FALSE);
if (DSA_NewRandom(NULL, &key->params.subPrime, &t2) != SECSuccess) {
PORT_SetError(SEC_ERROR_NEED_RANDOM);
rv = SECFailure;
goto cleanup;
}
SECITEM_TO_MPINT(t2, &ar); /* ar <-$ Zq */
- SECITEM_FreeItem(&t2, PR_FALSE);
+ SECITEM_ZfreeItem(&t2, PR_FALSE);
/* Using mp_invmod on k directly would leak bits from k. */
CHECK_MPI_OK(mp_mul(&k, &ar, &k)); /* k = k * ar */
@@ -530,6 +532,7 @@ DSA_SignDigest(DSAPrivateKey *key, SECItem *signature, const SECItem *digest)
rv = dsa_SignDigest(key, signature, digest, kSeed);
} while (rv != SECSuccess && PORT_GetError() == SEC_ERROR_NEED_RANDOM &&
--retries > 0);
+ PORT_Memset(kSeed, 0, sizeof kSeed);
return rv;
}
@@ -670,6 +673,7 @@ DSA_VerifyDigest(DSAPublicKey *key, const SECItem *signature,
verified = SECSuccess; /* Signature verified. */
}
cleanup:
+ PORT_Memset(localDigestData, 0, sizeof localDigestData);
mp_clear(&p);
mp_clear(&q);
mp_clear(&g);
diff --git a/lib/freebl/ec.c b/lib/freebl/ec.c
index 7f4e903a0..73a625a69 100644
--- a/lib/freebl/ec.c
+++ b/lib/freebl/ec.c
@@ -7,6 +7,7 @@
#endif
#include "blapi.h"
+#include "blapii.h"
#include "prerr.h"
#include "secerr.h"
#include "secmpi.h"
@@ -146,6 +147,10 @@ ec_points_mul(const ECParams *params, const mp_int *k1, const mp_int *k2,
CHECK_MPI_OK(ECPoints_mul(group, k1, NULL, NULL, NULL, &Qx, &Qy));
}
+ /* our ECC codes uses large stack variables to store intermediate results,
+ * clear our stack before returning to prevent CSP leakage */
+ BLAPI_CLEAR_STACK(2048)
+
/* Construct the SECItem representation of point Q */
pointQ->data[0] = EC_POINT_FORM_UNCOMPRESSED;
CHECK_MPI_OK(mp_to_fixlen_octets(&Qx, pointQ->data + 1,
@@ -531,7 +536,6 @@ ECDH_Derive(SECItem *publicValue,
unsigned int len = 0;
SECItem pointQ = { siBuffer, NULL, 0 };
mp_int k; /* to hold the private value */
- mp_int cofactor;
mp_err err = MP_OKAY;
#if EC_DEBUG
int i;
@@ -596,11 +600,13 @@ ECDH_Derive(SECItem *publicValue,
(mp_size)privateValue->len));
if (withCofactor && (ecParams->cofactor != 1)) {
+ mp_int cofactor;
/* multiply k with the cofactor */
MP_DIGITS(&cofactor) = 0;
CHECK_MPI_OK(mp_init(&cofactor));
mp_set(&cofactor, ecParams->cofactor);
CHECK_MPI_OK(mp_mul(&k, &cofactor, &k));
+ mp_clear(&cofactor);
}
/* Multiply our private key and peer's public point */
@@ -858,7 +864,7 @@ cleanup:
mp_clear(&ar);
if (t2) {
- PORT_Free(t2);
+ PORT_ZFree(t2, 2 * ecParams->order.len);
}
if (kGpoint.data) {
diff --git a/lib/freebl/ecl/ecp_jm.c b/lib/freebl/ecl/ecp_jm.c
index bd13fa050..799842171 100644
--- a/lib/freebl/ecl/ecp_jm.c
+++ b/lib/freebl/ecl/ecp_jm.c
@@ -192,7 +192,7 @@ ec_GFp_pt_mul_jm_wNAF(const mp_int *n, const mp_int *px, const mp_int *py,
mp_int raz4;
mp_int scratch[MAX_SCRATCH];
signed char *naf = NULL;
- int i, orderBitSize;
+ int i, orderBitSize = 0;
MP_DIGITS(&rz) = 0;
MP_DIGITS(&raz4) = 0;
@@ -289,6 +289,9 @@ CLEANUP:
mp_clear(&tpy);
mp_clear(&rz);
mp_clear(&raz4);
+ if (naf) {
+ memset(naf, 0, orderBitSize + 1);
+ }
free(naf);
return res;
}
diff --git a/lib/freebl/gcm.c b/lib/freebl/gcm.c
index c2cc18d91..ac461b488 100644
--- a/lib/freebl/gcm.c
+++ b/lib/freebl/gcm.c
@@ -593,15 +593,19 @@ GCM_CreateContext(void *context, freeblCipherFunc cipher,
if (rv != SECSuccess) {
goto loser;
}
+ PORT_Memset(H, 0, AES_BLOCK_SIZE);
gcm->ctr_context_init = PR_TRUE;
return gcm;
loser:
+ PORT_Memset(H, 0, AES_BLOCK_SIZE);
if (ghash && ghash->mem) {
- PORT_Free(ghash->mem);
+ void *mem = ghash->mem;
+ PORT_Memset(ghash, 0, sizeof(gcmHashContext));
+ PORT_Free(mem);
}
if (gcm) {
- PORT_Free(gcm);
+ PORT_ZFree(gcm, sizeof(GCMContext));
}
return NULL;
}
@@ -675,9 +679,11 @@ gcm_InitCounter(GCMContext *gcm, const unsigned char *iv, unsigned int ivLen,
goto loser;
}
+ PORT_Memset(&ctrParams, 0, sizeof ctrParams);
return SECSuccess;
loser:
+ PORT_Memset(&ctrParams, 0, sizeof ctrParams);
if (freeCtr) {
CTR_DestroyContext(&gcm->ctr_context, PR_FALSE);
}
@@ -687,13 +693,15 @@ loser:
void
GCM_DestroyContext(GCMContext *gcm, PRBool freeit)
{
- /* these two are statically allocated and will be freed when we free
+ void *mem = gcm->ghash_context->mem;
+ /* ctr_context is statically allocated and will be freed when we free
* gcm. call their destroy functions to free up any locally
* allocated data (like mp_int's) */
if (gcm->ctr_context_init) {
CTR_DestroyContext(&gcm->ctr_context, PR_FALSE);
}
- PORT_Free(gcm->ghash_context->mem);
+ PORT_Memset(gcm->ghash_context, 0, sizeof(gcmHashContext));
+ PORT_Free(mem);
PORT_Memset(&gcm->tagBits, 0, sizeof(gcm->tagBits));
PORT_Memset(gcm->tagKey, 0, sizeof(gcm->tagKey));
if (freeit) {
diff --git a/lib/freebl/hmacct.c b/lib/freebl/hmacct.c
index fac323e85..a1b2ba35a 100644
--- a/lib/freebl/hmacct.c
+++ b/lib/freebl/hmacct.c
@@ -274,6 +274,11 @@ MAC(unsigned char *mdOut,
hashObj->end(mdState, mdOut, mdOutLen, mdOutMax);
hashObj->destroy(mdState, PR_TRUE);
+ PORT_Memset(lengthBytes, 0, sizeof lengthBytes);
+ PORT_Memset(hmacPad, 0, sizeof hmacPad);
+ PORT_Memset(firstBlock, 0, sizeof firstBlock);
+ PORT_Memset(macOut, 0, sizeof macOut);
+
return SECSuccess;
}
diff --git a/lib/freebl/mpi/mpmontg.c b/lib/freebl/mpi/mpmontg.c
index 3acdc9fef..79104f7b9 100644
--- a/lib/freebl/mpi/mpmontg.c
+++ b/lib/freebl/mpi/mpmontg.c
@@ -1006,7 +1006,11 @@ CLEANUP:
mp_clear(&accum[2]);
mp_clear(&accum[3]);
mp_clear(&tmp);
- /* PORT_Memset(powers,0,num_powers*nLen*sizeof(mp_digit)); */
+ /* zero required by FIPS here, can't use PORT_ZFree
+ * because mpi doesn't link with util */
+ if (powers) {
+ PORT_Memset(powers, 0, num_powers * sizeof(mp_digit));
+ }
free(powersArray);
return res;
}
diff --git a/lib/freebl/pqg.c b/lib/freebl/pqg.c
index 626b2fb85..1b03278a2 100644
--- a/lib/freebl/pqg.c
+++ b/lib/freebl/pqg.c
@@ -711,7 +711,7 @@ cleanup:
if (rv == SECFailure) {
mp_zero(prime);
if (prime_seed->data) {
- SECITEM_FreeItem(prime_seed, PR_FALSE);
+ SECITEM_ZfreeItem(prime_seed, PR_FALSE);
}
*prime_gen_counter = 0;
}
@@ -867,7 +867,7 @@ cleanup:
if (rv == SECFailure) {
mp_zero(prime);
if (prime_seed->data) {
- SECITEM_FreeItem(prime_seed, PR_FALSE);
+ SECITEM_ZfreeItem(prime_seed, PR_FALSE);
}
*prime_gen_counter = 0;
}
@@ -905,6 +905,7 @@ findQfromSeed(
*typePtr = FIPS186_1_TYPE;
return SECSuccess;
}
+ mp_zero(Q_);
return SECFailure;
}
/* 1024 could use FIPS186_1 or FIPS186_3 algorithms, we need to try
@@ -954,21 +955,23 @@ findQfromSeed(
if ((offset < 0) ||
(PORT_Memcmp(&seed->data[offset], qseed.data, qseed.len) != 0)) {
/* we found q, but the seeds don't match. This isn't an
- * accident, someone has been tweeking with the seeds, just
- * fail a this point. */
+ * accident, someone has been tweeking with the seeds, just
+ * fail a this point. */
SECITEM_FreeItem(&qseed, PR_FALSE);
+ mp_zero(Q_);
return SECFailure;
}
*qseed_len = qseed.len;
*hashtypePtr = hashtype;
*typePtr = FIPS186_3_ST_TYPE;
*qgen_counter = count;
- SECITEM_FreeItem(&qseed, PR_FALSE);
+ SECITEM_ZfreeItem(&qseed, PR_FALSE);
return SECSuccess;
}
- SECITEM_FreeItem(&qseed, PR_FALSE);
+ SECITEM_ZfreeItem(&qseed, PR_FALSE);
}
/* no hash algorithms found which match seed to Q, fail */
+ mp_zero(Q_);
return SECFailure;
}
@@ -1069,6 +1072,7 @@ makePfromQandSeed(
CHECK_MPI_OK(mp_sub_d(&c, 1, &c)); /* c -= 1 */
CHECK_MPI_OK(mp_sub(&X, &c, P)); /* P = X - c */
cleanup:
+ PORT_Memset(V_j, 0, sizeof V_j);
mp_clear(&W);
mp_clear(&X);
mp_clear(&c);
@@ -1077,8 +1081,12 @@ cleanup:
mp_clear(&tmp);
if (err) {
MP_TO_SEC_ERROR(err);
+ mp_zero(P);
return SECFailure;
}
+ if (rv != SECSuccess) {
+ mp_zero(P);
+ }
return rv;
}
@@ -1128,6 +1136,9 @@ cleanup:
MP_TO_SEC_ERROR(err);
rv = SECFailure;
}
+ if (rv != SECSuccess) {
+ mp_zero(G);
+ }
return rv;
}
@@ -1534,10 +1545,10 @@ generate_G:
*pVfy = verify;
cleanup:
if (pseed.data) {
- PORT_Free(pseed.data);
+ SECITEM_ZfreeItem(&pseed, PR_FALSE);
}
if (qseed.data) {
- PORT_Free(qseed.data);
+ SECITEM_ZfreeItem(&qseed, PR_FALSE);
}
mp_clear(&P);
mp_clear(&Q);
@@ -1558,7 +1569,7 @@ cleanup:
}
}
if (hit.data) {
- SECITEM_FreeItem(&hit, PR_FALSE);
+ SECITEM_ZfreeItem(&hit, PR_FALSE);
}
return rv;
}
@@ -1869,7 +1880,7 @@ cleanup:
mp_clear(&r);
mp_clear(&h);
if (pseed_.data) {
- SECITEM_FreeItem(&pseed_, PR_FALSE);
+ SECITEM_ZfreeItem(&pseed_, PR_FALSE);
}
if (err) {
MP_TO_SEC_ERROR(err);
@@ -1887,11 +1898,11 @@ PQG_DestroyParams(PQGParams *params)
if (params == NULL)
return;
if (params->arena != NULL) {
- PORT_FreeArena(params->arena, PR_FALSE); /* don't zero it */
+ PORT_FreeArena(params->arena, PR_TRUE);
} else {
- SECITEM_FreeItem(&params->prime, PR_FALSE); /* don't free prime */
- SECITEM_FreeItem(&params->subPrime, PR_FALSE); /* don't free subPrime */
- SECITEM_FreeItem(&params->base, PR_FALSE); /* don't free base */
+ SECITEM_ZfreeItem(&params->prime, PR_FALSE); /* don't free prime */
+ SECITEM_ZfreeItem(&params->subPrime, PR_FALSE); /* don't free subPrime */
+ SECITEM_ZfreeItem(&params->base, PR_FALSE); /* don't free base */
PORT_Free(params);
}
}
@@ -1906,10 +1917,10 @@ PQG_DestroyVerify(PQGVerify *vfy)
if (vfy == NULL)
return;
if (vfy->arena != NULL) {
- PORT_FreeArena(vfy->arena, PR_FALSE); /* don't zero it */
+ PORT_FreeArena(vfy->arena, PR_TRUE);
} else {
- SECITEM_FreeItem(&vfy->seed, PR_FALSE); /* don't free seed */
- SECITEM_FreeItem(&vfy->h, PR_FALSE); /* don't free h */
+ SECITEM_ZfreeItem(&vfy->seed, PR_FALSE); /* don't free seed */
+ SECITEM_ZfreeItem(&vfy->h, PR_FALSE); /* don't free h */
PORT_Free(vfy);
}
}
diff --git a/lib/freebl/rijndael.c b/lib/freebl/rijndael.c
index 449557cbe..546731f9d 100644
--- a/lib/freebl/rijndael.c
+++ b/lib/freebl/rijndael.c
@@ -957,6 +957,7 @@ aes_InitContext(AESContext *cx, const unsigned char *key, unsigned int keysize,
} else {
rijndael_invkey_expansion(cx, key, Nk);
}
+ BLAPI_CLEAR_STACK(256)
}
cx->worker_cx = cx;
cx->destroy = NULL;
@@ -1118,6 +1119,7 @@ AES_Encrypt(AESContext *cx, unsigned char *output,
const unsigned char *input, unsigned int inputLen)
{
/* Check args */
+ SECStatus rv;
if (cx == NULL || output == NULL || (input == NULL && inputLen != 0)) {
PORT_SetError(SEC_ERROR_INVALID_ARGS);
return SECFailure;
@@ -1152,8 +1154,10 @@ AES_Encrypt(AESContext *cx, unsigned char *output,
}
#endif
- return (*cx->worker)(cx->worker_cx, output, outputLen, maxOutputLen,
- input, inputLen, AES_BLOCK_SIZE);
+ rv = (*cx->worker)(cx->worker_cx, output, outputLen, maxOutputLen,
+ input, inputLen, AES_BLOCK_SIZE);
+ BLAPI_CLEAR_STACK(256)
+ return rv;
}
/*
@@ -1167,6 +1171,7 @@ AES_Decrypt(AESContext *cx, unsigned char *output,
unsigned int *outputLen, unsigned int maxOutputLen,
const unsigned char *input, unsigned int inputLen)
{
+ SECStatus rv;
/* Check args */
if (cx == NULL || output == NULL || (input == NULL && inputLen != 0)) {
PORT_SetError(SEC_ERROR_INVALID_ARGS);
@@ -1181,8 +1186,10 @@ AES_Decrypt(AESContext *cx, unsigned char *output,
return SECFailure;
}
*outputLen = inputLen;
- return (*cx->worker)(cx->worker_cx, output, outputLen, maxOutputLen,
- input, inputLen, AES_BLOCK_SIZE);
+ rv = (*cx->worker)(cx->worker_cx, output, outputLen, maxOutputLen,
+ input, inputLen, AES_BLOCK_SIZE);
+ BLAPI_CLEAR_STACK(256)
+ return rv;
}
/*
@@ -1197,6 +1204,7 @@ AES_AEAD(AESContext *cx, unsigned char *output,
void *params, unsigned int paramsLen,
const unsigned char *aad, unsigned int aadLen)
{
+ SECStatus rv;
/* Check args */
if (cx == NULL || output == NULL || (input == NULL && inputLen != 0) || (aad == NULL && aadLen != 0) || params == NULL) {
PORT_SetError(SEC_ERROR_INVALID_ARGS);
@@ -1232,7 +1240,9 @@ AES_AEAD(AESContext *cx, unsigned char *output,
}
#endif
- return (*cx->worker_aead)(cx->worker_cx, output, outputLen, maxOutputLen,
- input, inputLen, params, paramsLen, aad, aadLen,
- AES_BLOCK_SIZE);
+ rv = (*cx->worker_aead)(cx->worker_cx, output, outputLen, maxOutputLen,
+ input, inputLen, params, paramsLen, aad, aadLen,
+ AES_BLOCK_SIZE);
+ BLAPI_CLEAR_STACK(256)
+ return rv;
}
diff --git a/lib/freebl/rsa.c b/lib/freebl/rsa.c
index a08636de6..5a4e4096f 100644
--- a/lib/freebl/rsa.c
+++ b/lib/freebl/rsa.c
@@ -1593,7 +1593,7 @@ RSA_Cleanup(void)
mp_clear(&bp->f);
mp_clear(&bp->g);
}
- SECITEM_FreeItem(&rsabp->modulus, PR_FALSE);
+ SECITEM_ZfreeItem(&rsabp->modulus, PR_FALSE);
PORT_Free(rsabp);
}
diff --git a/lib/freebl/rsapkcs.c b/lib/freebl/rsapkcs.c
index 0bf1f97cb..469db3fef 100644
--- a/lib/freebl/rsapkcs.c
+++ b/lib/freebl/rsapkcs.c
@@ -147,7 +147,7 @@ rsa_FormatOneBlock(unsigned modulusLen,
padLen = modulusLen - data->len - 3;
PORT_Assert(padLen >= RSA_BLOCK_MIN_PAD_LEN);
if (padLen < RSA_BLOCK_MIN_PAD_LEN) {
- PORT_Free(block);
+ PORT_ZFree(block, modulusLen);
return NULL;
}
PORT_Memset(bp, RSA_BLOCK_PRIVATE_PAD_OCTET, padLen);
@@ -176,7 +176,7 @@ rsa_FormatOneBlock(unsigned modulusLen,
padLen = modulusLen - (data->len + 3);
PORT_Assert(padLen >= RSA_BLOCK_MIN_PAD_LEN);
if (padLen < RSA_BLOCK_MIN_PAD_LEN) {
- PORT_Free(block);
+ PORT_ZFree(block, modulusLen);
return NULL;
}
j = modulusLen - 2;
@@ -205,7 +205,7 @@ rsa_FormatOneBlock(unsigned modulusLen,
}
}
if (rv != SECSuccess) {
- PORT_Free(block);
+ PORT_ZFree(block, modulusLen);
PORT_SetError(SEC_ERROR_LIBRARY_FAILURE);
return NULL;
}
@@ -216,7 +216,7 @@ rsa_FormatOneBlock(unsigned modulusLen,
default:
PORT_Assert(0);
- PORT_Free(block);
+ PORT_ZFree(block, modulusLen);
return NULL;
}
diff --git a/lib/freebl/shvfy.c b/lib/freebl/shvfy.c
index 98db4614b..da42467fd 100644
--- a/lib/freebl/shvfy.c
+++ b/lib/freebl/shvfy.c
@@ -18,6 +18,7 @@
#include "hasht.h"
#include "pqg.h"
#include "blapii.h"
+#include "secitem.h"
#ifndef NSS_FIPS_DISABLED
@@ -494,6 +495,8 @@ blapi_SHVerifyFile(const char *shName, PRBool self)
#endif /* DEBUG_SHVERIFY */
loser:
+ PORT_Memset(buf, 0, sizeof buf);
+ PORT_Memset(hashBuf, 0, sizeof hashBuf);
if (checkName != NULL) {
PORT_Free(checkName);
}
@@ -509,19 +512,19 @@ loser:
}
}
if (signature.data != NULL) {
- PORT_Free(signature.data);
+ SECITEM_ZfreeItem(&signature, PR_FALSE);
}
if (key.params.prime.data != NULL) {
- PORT_Free(key.params.prime.data);
+ SECITEM_ZfreeItem(&key.params.prime, PR_FALSE);
}
if (key.params.subPrime.data != NULL) {
- PORT_Free(key.params.subPrime.data);
+ SECITEM_ZfreeItem(&key.params.subPrime, PR_FALSE);
}
if (key.params.base.data != NULL) {
- PORT_Free(key.params.base.data);
+ SECITEM_ZfreeItem(&key.params.base, PR_FALSE);
}
if (key.publicValue.data != NULL) {
- PORT_Free(key.publicValue.data);
+ SECITEM_ZfreeItem(&key.publicValue, PR_FALSE);
}
return result;
diff --git a/lib/freebl/unix_urandom.c b/lib/freebl/unix_urandom.c
index 720fa80bb..73006cdbb 100644
--- a/lib/freebl/unix_urandom.c
+++ b/lib/freebl/unix_urandom.c
@@ -22,6 +22,7 @@ RNG_SystemInfoForRNG(void)
return;
}
RNG_RandomUpdate(bytes, numBytes);
+ PORT_Memset(bytes, 0, sizeof bytes);
}
size_t
diff --git a/lib/softoken/fipstokn.c b/lib/softoken/fipstokn.c
index 6ffec5de1..1dabc59e2 100644
--- a/lib/softoken/fipstokn.c
+++ b/lib/softoken/fipstokn.c
@@ -650,7 +650,7 @@ FC_GetMechanismList(CK_SLOT_ID slotID,
CHECK_FORK();
SFTK_FIPSFATALCHECK();
- if ((slotID == FIPS_SLOT_ID) || (slotID >= SFTK_MIN_FIPS_USER_SLOT_ID)) {
+ if (sftk_isFIPS(slotID)) {
slotID = NETSCAPE_SLOT_ID;
}
/* FIPS Slots support all functions */
@@ -666,7 +666,7 @@ FC_GetMechanismInfo(CK_SLOT_ID slotID, CK_MECHANISM_TYPE type,
CHECK_FORK();
SFTK_FIPSFATALCHECK();
- if ((slotID == FIPS_SLOT_ID) || (slotID >= SFTK_MIN_FIPS_USER_SLOT_ID)) {
+ if (sftk_isFIPS(slotID)) {
slotID = NETSCAPE_SLOT_ID;
}
/* FIPS Slots support all functions */
@@ -682,7 +682,7 @@ FC_GetMechanismInfoV2(CK_SLOT_ID slotID, CK_MECHANISM_TYPE type,
CHECK_FORK();
SFTK_FIPSFATALCHECK();
- if ((slotID == FIPS_SLOT_ID) || (slotID >= SFTK_MIN_FIPS_USER_SLOT_ID)) {
+ if (sftk_isFIPS(slotID)) {
slotID = NETSCAPE_SLOT_ID;
}
/* FIPS Slots support all functions */
diff --git a/lib/softoken/lowkey.c b/lib/softoken/lowkey.c
index e9bbff1d9..1eba1ad8f 100644
--- a/lib/softoken/lowkey.c
+++ b/lib/softoken/lowkey.c
@@ -220,7 +220,7 @@ void
nsslowkey_DestroyPublicKey(NSSLOWKEYPublicKey *pubk)
{
if (pubk && pubk->arena) {
- PORT_FreeArena(pubk->arena, PR_FALSE);
+ PORT_FreeArena(pubk->arena, PR_TRUE);
}
}
unsigned
@@ -310,7 +310,7 @@ nsslowkey_ConvertToPublicKey(NSSLOWKEYPrivateKey *privk)
break;
}
rv = SECITEM_CopyItem(privk->arena, &privk->u.dsa.publicValue, &publicValue);
- SECITEM_FreeItem(&publicValue, PR_FALSE);
+ SECITEM_ZfreeItem(&publicValue, PR_FALSE);
if (rv != SECSuccess) {
break;
}
@@ -349,7 +349,7 @@ nsslowkey_ConvertToPublicKey(NSSLOWKEYPrivateKey *privk)
break;
}
rv = SECITEM_CopyItem(privk->arena, &privk->u.dh.publicValue, &publicValue);
- SECITEM_FreeItem(&publicValue, PR_FALSE);
+ SECITEM_ZfreeItem(&publicValue, PR_FALSE);
if (rv != SECSuccess) {
break;
}
@@ -394,7 +394,7 @@ nsslowkey_ConvertToPublicKey(NSSLOWKEYPrivateKey *privk)
break;
}
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
return NULL;
}
diff --git a/lib/softoken/lowpbe.c b/lib/softoken/lowpbe.c
index 0d8e02ddf..2ce6c415e 100644
--- a/lib/softoken/lowpbe.c
+++ b/lib/softoken/lowpbe.c
@@ -164,11 +164,11 @@ nsspkcs5_PBKDF1(const SECHashObject *hashObj, SECItem *salt, SECItem *pwd,
}
if (pre_hash != NULL) {
- SECITEM_FreeItem(pre_hash, PR_TRUE);
+ SECITEM_ZfreeItem(pre_hash, PR_TRUE);
}
if ((rv != SECSuccess) && (hash != NULL)) {
- SECITEM_FreeItem(hash, PR_TRUE);
+ SECITEM_ZfreeItem(hash, PR_TRUE);
hash = NULL;
}
@@ -297,7 +297,7 @@ nsspkcs5_PBKDF1Extended(const SECHashObject *hashObj,
newHash = nsspkcs5_PFXPBE(hashObj, pbe_param, hash, bytes_needed);
if (hash != newHash)
- SECITEM_FreeItem(hash, PR_TRUE);
+ SECITEM_ZfreeItem(hash, PR_TRUE);
return newHash;
}
@@ -403,7 +403,7 @@ loser:
PORT_ZFree(T, hLen);
}
if (rv != SECSuccess) {
- SECITEM_FreeItem(result, PR_TRUE);
+ SECITEM_ZfreeItem(result, PR_TRUE);
result = NULL;
} else {
result->len = dkLen;
@@ -598,7 +598,7 @@ sftk_clearPBECommonCacheItemsLocked(KDFCacheItem *item)
item->hash = NULL;
}
if (item->salt) {
- SECITEM_FreeItem(item->salt, PR_TRUE);
+ SECITEM_ZfreeItem(item->salt, PR_TRUE);
item->salt = NULL;
}
if (item->pwItem) {
@@ -1159,6 +1159,7 @@ nsspkcs5_AlgidToParam(SECAlgorithmID *algid)
}
loser:
+ PORT_Memset(&pbev2_param, 0, sizeof(pbev2_param));
if (rv == SECSuccess) {
pbe_param->iter = DER_GetInteger(&pbe_param->iteration);
} else {
@@ -1177,7 +1178,7 @@ void
nsspkcs5_DestroyPBEParameter(NSSPKCS5PBEParameter *pbe_param)
{
if (pbe_param != NULL) {
- PORT_FreeArena(pbe_param->poolp, PR_FALSE);
+ PORT_FreeArena(pbe_param->poolp, PR_TRUE);
}
}
@@ -1213,7 +1214,7 @@ sec_pkcs5_des(SECItem *key, SECItem *iv, SECItem *src, PRBool triple_des,
dummy = CBC_PadBuffer(NULL, dup_src->data,
dup_src->len, &dup_src->len, DES_BLOCK_SIZE);
if (dummy == NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
return NULL;
}
dup_src->data = (unsigned char *)dummy;
@@ -1247,13 +1248,13 @@ sec_pkcs5_des(SECItem *key, SECItem *iv, SECItem *src, PRBool triple_des,
loser:
if (crv != CKR_OK) {
if (dest != NULL) {
- SECITEM_FreeItem(dest, PR_TRUE);
+ SECITEM_ZfreeItem(dest, PR_TRUE);
}
dest = NULL;
}
if (dup_src != NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
}
return dest;
@@ -1289,7 +1290,7 @@ sec_pkcs5_aes(SECItem *key, SECItem *iv, SECItem *src, PRBool triple_des,
dummy = CBC_PadBuffer(NULL, dup_src->data,
dup_src->len, &dup_src->len, AES_BLOCK_SIZE);
if (dummy == NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
return NULL;
}
dup_src->data = (unsigned char *)dummy;
@@ -1322,13 +1323,13 @@ sec_pkcs5_aes(SECItem *key, SECItem *iv, SECItem *src, PRBool triple_des,
loser:
if (crv != CKR_OK) {
if (dest != NULL) {
- SECITEM_FreeItem(dest, PR_TRUE);
+ SECITEM_ZfreeItem(dest, PR_TRUE);
}
dest = NULL;
}
if (dup_src != NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
}
return dest;
@@ -1364,7 +1365,7 @@ sec_pkcs5_aes_key_wrap(SECItem *key, SECItem *iv, SECItem *src, PRBool triple_de
dummy = CBC_PadBuffer(NULL, dup_src->data,
dup_src->len, &dup_src->len, AES_BLOCK_SIZE);
if (dummy == NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
return NULL;
}
dup_src->data = (unsigned char *)dummy;
@@ -1398,13 +1399,13 @@ sec_pkcs5_aes_key_wrap(SECItem *key, SECItem *iv, SECItem *src, PRBool triple_de
loser:
if (crv != CKR_OK) {
if (dest != NULL) {
- SECITEM_FreeItem(dest, PR_TRUE);
+ SECITEM_ZfreeItem(dest, PR_TRUE);
}
dest = NULL;
}
if (dup_src != NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
}
return dest;
@@ -1438,7 +1439,7 @@ sec_pkcs5_rc2(SECItem *key, SECItem *iv, SECItem *src, PRBool dummy,
v = CBC_PadBuffer(NULL, dup_src->data,
dup_src->len, &dup_src->len, 8 /* RC2_BLOCK_SIZE */);
if (v == NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
return NULL;
}
dup_src->data = (unsigned char *)v;
@@ -1478,12 +1479,12 @@ sec_pkcs5_rc2(SECItem *key, SECItem *iv, SECItem *src, PRBool dummy,
}
if ((rv != SECSuccess) && (dest != NULL)) {
- SECITEM_FreeItem(dest, PR_TRUE);
+ SECITEM_ZfreeItem(dest, PR_TRUE);
dest = NULL;
}
if (dup_src != NULL) {
- SECITEM_FreeItem(dup_src, PR_TRUE);
+ SECITEM_ZfreeItem(dup_src, PR_TRUE);
}
return dest;
@@ -1521,7 +1522,7 @@ sec_pkcs5_rc4(SECItem *key, SECItem *iv, SECItem *src, PRBool dummy_op,
}
if ((rv != SECSuccess) && (dest)) {
- SECITEM_FreeItem(dest, PR_TRUE);
+ SECITEM_ZfreeItem(dest, PR_TRUE);
dest = NULL;
}
diff --git a/lib/softoken/pkcs11.c b/lib/softoken/pkcs11.c
index 33dacc6da..ba17298a9 100644
--- a/lib/softoken/pkcs11.c
+++ b/lib/softoken/pkcs11.c
@@ -1177,7 +1177,7 @@ sftk_handlePrivateKeyObject(SFTKSession *session, SFTKObject *object, CK_KEY_TYP
crv = sftk_forceAttribute(object, CKA_NSS_DB,
sftk_item_expand(&mod));
if (mod.data)
- PORT_Free(mod.data);
+ SECITEM_ZfreeItem(&mod, PR_FALSE);
if (crv != CKR_OK)
return crv;
@@ -1497,7 +1497,7 @@ sftk_handleKeyObject(SFTKSession *session, SFTKObject *object)
case CKO_SECRET_KEY:
/* make sure the required fields exist */
return sftk_handleSecretKeyObject(session, object, key_type,
- (PRBool)(session->slot->slotID == FIPS_SLOT_ID));
+ (PRBool)(sftk_isFIPS(session->slot->slotID)));
default:
break;
}
@@ -1939,7 +1939,7 @@ sftk_GetPubKey(SFTKObject *object, CK_KEY_TYPE key_type,
}
*crvp = crv;
if (crv != CKR_OK) {
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
return NULL;
}
@@ -2099,7 +2099,7 @@ sftk_mkPrivKey(SFTKObject *object, CK_KEY_TYPE key_type, CK_RV *crvp)
}
*crvp = crv;
if (crv != CKR_OK) {
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
return NULL;
}
return privKey;
@@ -2604,7 +2604,7 @@ static PLHashTable *nscSlotHashTable[2] = { NULL, NULL };
static unsigned int
sftk_GetModuleIndex(CK_SLOT_ID slotID)
{
- if ((slotID == FIPS_SLOT_ID) || (slotID >= SFTK_MIN_FIPS_USER_SLOT_ID)) {
+ if (sftk_isFIPS(slotID)) {
return NSC_FIPS_MODULE;
}
return NSC_NON_FIPS_MODULE;
@@ -4031,6 +4031,7 @@ NSC_InitPIN(CK_SESSION_HANDLE hSession,
if (tokenRemoved) {
sftk_CloseAllSessions(slot, PR_FALSE);
}
+ PORT_Memset(newPinStr, 0, ulPinLen);
sftk_freeDB(handle);
handle = NULL;
@@ -4122,10 +4123,12 @@ NSC_SetPIN(CK_SESSION_HANDLE hSession, CK_CHAR_PTR pOldPin,
/* change the data base password */
PR_Lock(slot->pwCheckLock);
rv = sftkdb_ChangePassword(handle, oldPinStr, newPinStr, &tokenRemoved);
+ PORT_Memset(newPinStr, 0, ulNewLen);
+ PORT_Memset(oldPinStr, 0, ulOldLen);
if (tokenRemoved) {
sftk_CloseAllSessions(slot, PR_FALSE);
}
- if ((rv != SECSuccess) && (slot->slotID == FIPS_SLOT_ID)) {
+ if ((rv != SECSuccess) && (sftk_isFIPS(slot->slotID))) {
PR_Sleep(loginWaitTime);
}
PR_Unlock(slot->pwCheckLock);
@@ -4361,6 +4364,7 @@ NSC_Login(CK_SESSION_HANDLE hSession, CK_USER_TYPE userType,
handle = sftk_getKeyDB(slot);
if (handle == NULL) {
+ PORT_Memset(pinStr, 0, ulPinLen);
return CKR_USER_TYPE_INVALID;
}
@@ -4375,7 +4379,7 @@ NSC_Login(CK_SESSION_HANDLE hSession, CK_USER_TYPE userType,
* key database */
if (((userType == CKU_SO) && (sessionFlags & CKF_RW_SESSION))
/* fips always needs to authenticate, even if there isn't a db */
- || (slot->slotID == FIPS_SLOT_ID)) {
+ || (sftk_isFIPS(slot->slotID))) {
/* should this be a fixed password? */
if (ulPinLen == 0) {
sftkdb_ClearPassword(handle);
@@ -4406,7 +4410,7 @@ NSC_Login(CK_SESSION_HANDLE hSession, CK_USER_TYPE userType,
if (tokenRemoved) {
sftk_CloseAllSessions(slot, PR_FALSE);
}
- if ((rv != SECSuccess) && (slot->slotID == FIPS_SLOT_ID)) {
+ if ((rv != SECSuccess) && (sftk_isFIPS(slot->slotID))) {
PR_Sleep(loginWaitTime);
}
PR_Unlock(slot->pwCheckLock);
@@ -4427,6 +4431,7 @@ NSC_Login(CK_SESSION_HANDLE hSession, CK_USER_TYPE userType,
crv = CKR_PIN_INCORRECT;
done:
+ PORT_Memset(pinStr, 0, ulPinLen);
if (handle) {
sftk_freeDB(handle);
}
diff --git a/lib/softoken/pkcs11c.c b/lib/softoken/pkcs11c.c
index 9709f4339..977880ed2 100644
--- a/lib/softoken/pkcs11c.c
+++ b/lib/softoken/pkcs11c.c
@@ -103,6 +103,13 @@ sftk_Space(void *data, PRBool freeit)
PORT_Free(data);
}
+static void
+sftk_ZSpace(void *data, PRBool freeit)
+{
+ size_t len = *(size_t *)data;
+ PORT_ZFree(data, len);
+}
+
/*
* turn a CDMF key into a des key. CDMF is an old IBM scheme to export DES by
* Deprecating a full des key to 40 bit key strenth.
@@ -117,6 +124,7 @@ sftk_cdmf2des(unsigned char *cdmfkey, unsigned char *deskey)
unsigned int leng, i;
DESContext *descx;
SECStatus rv;
+ CK_RV crv = CKR_OK;
/* zero the parity bits */
for (i = 0; i < 8; i++) {
@@ -125,12 +133,16 @@ sftk_cdmf2des(unsigned char *cdmfkey, unsigned char *deskey)
/* encrypt with key 1 */
descx = DES_CreateContext(key1, NULL, NSS_DES, PR_TRUE);
- if (descx == NULL)
- return CKR_HOST_MEMORY;
+ if (descx == NULL) {
+ crv = CKR_HOST_MEMORY;
+ goto done;
+ }
rv = DES_Encrypt(descx, enc_dest, &leng, 8, enc_src, 8);
DES_DestroyContext(descx, PR_TRUE);
- if (rv != SECSuccess)
- return sftk_MapCryptError(PORT_GetError());
+ if (rv != SECSuccess) {
+ crv = sftk_MapCryptError(PORT_GetError());
+ goto done;
+ }
/* xor source with des, zero the parity bits and deprecate the key*/
for (i = 0; i < 8; i++) {
@@ -143,16 +155,23 @@ sftk_cdmf2des(unsigned char *cdmfkey, unsigned char *deskey)
/* encrypt with key 2 */
descx = DES_CreateContext(key2, NULL, NSS_DES, PR_TRUE);
- if (descx == NULL)
- return CKR_HOST_MEMORY;
+ if (descx == NULL) {
+ crv = CKR_HOST_MEMORY;
+ goto done;
+ }
rv = DES_Encrypt(descx, deskey, &leng, 8, enc_src, 8);
DES_DestroyContext(descx, PR_TRUE);
- if (rv != SECSuccess)
- return sftk_MapCryptError(PORT_GetError());
+ if (rv != SECSuccess) {
+ crv = sftk_MapCryptError(PORT_GetError());
+ goto done;
+ }
/* set the corret parity on our new des key */
sftk_FormatDESKey(deskey, 8);
- return CKR_OK;
+done:
+ PORT_Memset(enc_src, 0, sizeof enc_src);
+ PORT_Memset(enc_dest, 0, sizeof enc_dest);
+ return crv;
}
/* NSC_DestroyObject destroys an object. */
@@ -566,31 +585,38 @@ sftk_RSADecrypt(NSSLOWKEYPrivateKey *key, unsigned char *output,
return rv;
}
+static void
+sftk_freeRSAOAEPInfo(SFTKOAEPInfo *info, PRBool freeit)
+{
+ PORT_ZFree(info->params.pSourceData, info->params.ulSourceDataLen);
+ PORT_ZFree(info, sizeof(SFTKOAEPInfo));
+}
+
static SECStatus
-sftk_RSAEncryptOAEP(SFTKOAEPEncryptInfo *info, unsigned char *output,
+sftk_RSAEncryptOAEP(SFTKOAEPInfo *info, unsigned char *output,
unsigned int *outputLen, unsigned int maxLen,
const unsigned char *input, unsigned int inputLen)
{
HASH_HashType hashAlg;
HASH_HashType maskHashAlg;
- PORT_Assert(info->key->keyType == NSSLOWKEYRSAKey);
- if (info->key->keyType != NSSLOWKEYRSAKey) {
+ PORT_Assert(info->key.pub->keyType == NSSLOWKEYRSAKey);
+ if (info->key.pub->keyType != NSSLOWKEYRSAKey) {
PORT_SetError(SEC_ERROR_INVALID_KEY);
return SECFailure;
}
- hashAlg = GetHashTypeFromMechanism(info->params->hashAlg);
- maskHashAlg = GetHashTypeFromMechanism(info->params->mgf);
+ hashAlg = GetHashTypeFromMechanism(info->params.hashAlg);
+ maskHashAlg = GetHashTypeFromMechanism(info->params.mgf);
- return RSA_EncryptOAEP(&info->key->u.rsa, hashAlg, maskHashAlg,
- (const unsigned char *)info->params->pSourceData,
- info->params->ulSourceDataLen, NULL, 0,
+ return RSA_EncryptOAEP(&info->key.pub->u.rsa, hashAlg, maskHashAlg,
+ (const unsigned char *)info->params.pSourceData,
+ info->params.ulSourceDataLen, NULL, 0,
output, outputLen, maxLen, input, inputLen);
}
static SECStatus
-sftk_RSADecryptOAEP(SFTKOAEPDecryptInfo *info, unsigned char *output,
+sftk_RSADecryptOAEP(SFTKOAEPInfo *info, unsigned char *output,
unsigned int *outputLen, unsigned int maxLen,
const unsigned char *input, unsigned int inputLen)
{
@@ -598,18 +624,18 @@ sftk_RSADecryptOAEP(SFTKOAEPDecryptInfo *info, unsigned char *output,
HASH_HashType hashAlg;
HASH_HashType maskHashAlg;
- PORT_Assert(info->key->keyType == NSSLOWKEYRSAKey);
- if (info->key->keyType != NSSLOWKEYRSAKey) {
+ PORT_Assert(info->key.priv->keyType == NSSLOWKEYRSAKey);
+ if (info->key.priv->keyType != NSSLOWKEYRSAKey) {
PORT_SetError(SEC_ERROR_INVALID_KEY);
return SECFailure;
}
- hashAlg = GetHashTypeFromMechanism(info->params->hashAlg);
- maskHashAlg = GetHashTypeFromMechanism(info->params->mgf);
+ hashAlg = GetHashTypeFromMechanism(info->params.hashAlg);
+ maskHashAlg = GetHashTypeFromMechanism(info->params.mgf);
- rv = RSA_DecryptOAEP(&info->key->u.rsa, hashAlg, maskHashAlg,
- (const unsigned char *)info->params->pSourceData,
- info->params->ulSourceDataLen,
+ rv = RSA_DecryptOAEP(&info->key.priv->u.rsa, hashAlg, maskHashAlg,
+ (const unsigned char *)info->params.pSourceData,
+ info->params.ulSourceDataLen,
output, outputLen, maxLen, input, inputLen);
if (rv != SECSuccess && PORT_GetError() == SEC_ERROR_LIBRARY_FAILURE) {
sftk_fatalError = PR_TRUE;
@@ -670,8 +696,10 @@ sftk_ChaCha20Poly1305_DestroyContext(SFTKChaCha20Poly1305Info *ctx,
{
ChaCha20Poly1305_DestroyContext(&ctx->freeblCtx, PR_FALSE);
if (ctx->adOverflow != NULL) {
- PORT_Free(ctx->adOverflow);
+ PORT_ZFree(ctx->adOverflow, ctx->adLen);
ctx->adOverflow = NULL;
+ } else {
+ PORT_Memset(ctx->ad, 0, ctx->adLen);
}
ctx->adLen = 0;
if (freeit) {
@@ -840,40 +868,54 @@ sftk_CryptInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMechanism,
}
context->multi = PR_FALSE;
context->rsa = PR_TRUE;
- if (isEncrypt) {
- SFTKOAEPEncryptInfo *info = PORT_New(SFTKOAEPEncryptInfo);
- if (info == NULL) {
- crv = CKR_HOST_MEMORY;
- break;
- }
- info->params = pMechanism->pParameter;
- info->key = sftk_GetPubKey(key, CKK_RSA, &crv);
- if (info->key == NULL) {
- PORT_Free(info);
- crv = CKR_KEY_HANDLE_INVALID;
- break;
+ {
+ SFTKOAEPInfo *info;
+ CK_RSA_PKCS_OAEP_PARAMS *params =
+ (CK_RSA_PKCS_OAEP_PARAMS *)pMechanism->pParameter;
+ /* make a copy of the source data value for future
+ * use (once the user has reclaimed his data in pParameter)*/
+ void *newSource = NULL;
+ if (params->pSourceData) {
+ newSource = PORT_Alloc(params->ulSourceDataLen);
+ if (newSource == NULL) {
+ crv = CKR_HOST_MEMORY;
+ break;
+ }
+ PORT_Memcpy(newSource, params->pSourceData, params->ulSourceDataLen);
}
- context->update = (SFTKCipher)sftk_RSAEncryptOAEP;
- context->maxLen = nsslowkey_PublicModulusLen(info->key);
- context->cipherInfo = info;
- } else {
- SFTKOAEPDecryptInfo *info = PORT_New(SFTKOAEPDecryptInfo);
+ info = PORT_New(SFTKOAEPInfo);
if (info == NULL) {
+ PORT_ZFree(newSource, params->ulSourceDataLen);
crv = CKR_HOST_MEMORY;
break;
}
- info->params = pMechanism->pParameter;
- info->key = sftk_GetPrivKey(key, CKK_RSA, &crv);
- if (info->key == NULL) {
- PORT_Free(info);
- crv = CKR_KEY_HANDLE_INVALID;
- break;
+ info->params = *params;
+ info->params.pSourceData = newSource;
+ info->isEncrypt = isEncrypt;
+
+ /* now setup encryption and decryption contexts */
+ if (isEncrypt) {
+ info->key.pub = sftk_GetPubKey(key, CKK_RSA, &crv);
+ if (info->key.pub == NULL) {
+ sftk_freeRSAOAEPInfo(info, PR_TRUE);
+ crv = CKR_KEY_HANDLE_INVALID;
+ break;
+ }
+ context->update = (SFTKCipher)sftk_RSAEncryptOAEP;
+ context->maxLen = nsslowkey_PublicModulusLen(info->key.pub);
+ } else {
+ info->key.priv = sftk_GetPrivKey(key, CKK_RSA, &crv);
+ if (info->key.priv == NULL) {
+ sftk_freeRSAOAEPInfo(info, PR_TRUE);
+ crv = CKR_KEY_HANDLE_INVALID;
+ break;
+ }
+ context->update = (SFTKCipher)sftk_RSADecryptOAEP;
+ context->maxLen = nsslowkey_PrivateModulusLen(info->key.priv);
}
- context->update = (SFTKCipher)sftk_RSADecryptOAEP;
- context->maxLen = nsslowkey_PrivateModulusLen(info->key);
context->cipherInfo = info;
}
- context->destroy = (SFTKDestroy)sftk_Space;
+ context->destroy = (SFTKDestroy)sftk_freeRSAOAEPInfo;
break;
#ifndef NSS_DISABLE_DEPRECATED_RC2
case CKM_RC2_CBC_PAD:
@@ -2058,7 +2100,7 @@ sftk_doMACInit(CK_MECHANISM_TYPE mech, SFTKSessionContext *session,
CK_RV crv;
sftk_MACCtx *context;
CK_ULONG *intpointer;
- PRBool isFIPS = (key->slot->slotID == FIPS_SLOT_ID);
+ PRBool isFIPS = sftk_isFIPS(key->slot->slotID);
/* Set up the initial context. */
crv = sftk_MAC_Create(mech, key, &context);
@@ -2146,6 +2188,7 @@ sftk_SSLMACSign(SFTKSSLMACInfo *info, unsigned char *sig, unsigned int *sigLen,
info->update(info->hashContext, hash, hashLen);
info->end(info->hashContext, tmpBuf, &out, SFTK_MAX_MAC_LENGTH);
PORT_Memcpy(sig, tmpBuf, info->macSize);
+ PORT_Memset(tmpBuf, 0, info->macSize);
*sigLen = info->macSize;
return SECSuccess;
}
@@ -2156,13 +2199,16 @@ sftk_SSLMACVerify(SFTKSSLMACInfo *info, unsigned char *sig, unsigned int sigLen,
{
unsigned char tmpBuf[SFTK_MAX_MAC_LENGTH];
unsigned int out;
+ int cmp;
info->begin(info->hashContext);
info->update(info->hashContext, info->key, info->keySize);
info->update(info->hashContext, ssl_pad_2, info->padSize);
info->update(info->hashContext, hash, hashLen);
info->end(info->hashContext, tmpBuf, &out, SFTK_MAX_MAC_LENGTH);
- return (NSS_SecureMemcmp(sig, tmpBuf, info->macSize) == 0) ? SECSuccess : SECFailure;
+ cmp = NSS_SecureMemcmp(sig, tmpBuf, info->macSize);
+ PORT_Memset(tmpBuf, 0, info->macSize);
+ return (cmp == 0) ? SECSuccess : SECFailure;
}
/*
@@ -2205,6 +2251,7 @@ sftk_doSSLMACInit(SFTKSessionContext *context, SECOidTag oid,
sftk_FreeAttribute(keyval);
return CKR_HOST_MEMORY;
}
+ sslmacinfo->size = sizeof(SFTKSSLMACInfo);
sslmacinfo->macSize = mac_size;
sslmacinfo->hashContext = context->hashInfo;
PORT_Memcpy(sslmacinfo->key, keyval->attrib.pValue,
@@ -2216,7 +2263,7 @@ sftk_doSSLMACInit(SFTKSessionContext *context, SECOidTag oid,
sslmacinfo->padSize = padSize;
sftk_FreeAttribute(keyval);
context->cipherInfo = (void *)sslmacinfo;
- context->destroy = (SFTKDestroy)sftk_Space;
+ context->destroy = (SFTKDestroy)sftk_ZSpace;
context->update = (SFTKCipher)sftk_SSLMACSign;
context->verify = (SFTKVerify)sftk_SSLMACVerify;
context->maxLen = mac_size;
@@ -2529,7 +2576,7 @@ RSA_HashSign(SECOidTag hashOid, NSSLOWKEYPrivateKey *key,
loser:
SGN_DestroyDigestInfo(di);
if (arena != NULL) {
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
}
return rv;
}
@@ -2577,14 +2624,14 @@ sftk_RSASignRaw(NSSLOWKEYPrivateKey *key, unsigned char *output,
}
static SECStatus
-sftk_RSASignPSS(SFTKHashSignInfo *info, unsigned char *sig,
+sftk_RSASignPSS(SFTKPSSSignInfo *info, unsigned char *sig,
unsigned int *sigLen, unsigned int maxLen,
const unsigned char *hash, unsigned int hashLen)
{
SECStatus rv = SECFailure;
HASH_HashType hashAlg;
HASH_HashType maskHashAlg;
- CK_RSA_PKCS_PSS_PARAMS *params = (CK_RSA_PKCS_PSS_PARAMS *)info->params;
+ CK_RSA_PKCS_PSS_PARAMS *params = &info->params;
PORT_Assert(info->key->keyType == NSSLOWKEYRSAKey);
if (info->key->keyType != NSSLOWKEYRSAKey) {
@@ -2706,6 +2753,7 @@ NSC_SignInit(CK_SESSION_HANDLE hSession,
CK_RV crv = CKR_OK;
NSSLOWKEYPrivateKey *privKey;
SFTKHashSignInfo *info = NULL;
+ SFTKPSSSignInfo *pinfo = NULL;
CHECK_FORK();
@@ -2814,21 +2862,22 @@ NSC_SignInit(CK_SESSION_HANDLE hSession,
crv = CKR_MECHANISM_PARAM_INVALID;
break;
}
- info = PORT_New(SFTKHashSignInfo);
- if (info == NULL) {
+ pinfo = PORT_New(SFTKPSSSignInfo);
+ if (pinfo == NULL) {
crv = CKR_HOST_MEMORY;
break;
}
- info->params = pMechanism->pParameter;
- info->key = sftk_GetPrivKey(key, CKK_RSA, &crv);
- if (info->key == NULL) {
- PORT_Free(info);
+ pinfo->size = sizeof(SFTKPSSSignInfo);
+ pinfo->params = *(CK_RSA_PKCS_PSS_PARAMS *)pMechanism->pParameter;
+ pinfo->key = sftk_GetPrivKey(key, CKK_RSA, &crv);
+ if (pinfo->key == NULL) {
+ crv = CKR_KEY_TYPE_INCONSISTENT;
break;
}
- context->cipherInfo = info;
- context->destroy = (SFTKDestroy)sftk_Space;
+ context->cipherInfo = pinfo;
+ context->destroy = (SFTKDestroy)sftk_ZSpace;
context->update = (SFTKCipher)sftk_RSASignPSS;
- context->maxLen = nsslowkey_PrivateModulusLen(info->key);
+ context->maxLen = nsslowkey_PrivateModulusLen(pinfo->key);
break;
#define INIT_DSA_SIG_MECH(mmm) \
@@ -3059,6 +3108,8 @@ NSC_SignInit(CK_SESSION_HANDLE hSession,
if (crv != CKR_OK) {
if (info)
PORT_Free(info);
+ if (pinfo)
+ PORT_ZFree(pinfo, pinfo->size);
sftk_FreeContext(context);
sftk_FreeSession(session);
return crv;
@@ -3272,6 +3323,7 @@ NSC_SignFinal(CK_SESSION_HANDLE hSession, CK_BYTE_PTR pSignature,
/* CKR_BUFFER_TOO_SMALL here isn't continuable, let operation terminate.
* Keeping "too small" CK_RV intact is a standard violation, but allows
* application read EXACT signature length */
+ PORT_Memset(tmpbuf, 0, sizeof tmpbuf);
} else {
/* must be block cipher MACing */
outlen = context->macSize;
@@ -3433,7 +3485,7 @@ RSA_HashCheckSign(SECOidTag digestOid, NSSLOWKEYPublicKey *key,
PR_FALSE /*XXX: unsafeAllowMissingParameters*/);
}
- PORT_Free(pkcs1DigestInfoData);
+ PORT_ZFree(pkcs1DigestInfoData, bufferSize);
return rv;
}
@@ -3466,13 +3518,13 @@ sftk_RSACheckSignRaw(NSSLOWKEYPublicKey *key, const unsigned char *sig,
}
static SECStatus
-sftk_RSACheckSignPSS(SFTKHashVerifyInfo *info, const unsigned char *sig,
+sftk_RSACheckSignPSS(SFTKPSSVerifyInfo *info, const unsigned char *sig,
unsigned int sigLen, const unsigned char *digest,
unsigned int digestLen)
{
HASH_HashType hashAlg;
HASH_HashType maskHashAlg;
- CK_RSA_PKCS_PSS_PARAMS *params = (CK_RSA_PKCS_PSS_PARAMS *)info->params;
+ CK_RSA_PKCS_PSS_PARAMS *params = &info->params;
PORT_Assert(info->key->keyType == NSSLOWKEYRSAKey);
if (info->key->keyType != NSSLOWKEYRSAKey) {
@@ -3501,6 +3553,7 @@ NSC_VerifyInit(CK_SESSION_HANDLE hSession,
CK_RV crv = CKR_OK;
NSSLOWKEYPublicKey *pubKey;
SFTKHashVerifyInfo *info = NULL;
+ SFTKPSSVerifyInfo *pinfo = NULL;
CHECK_FORK();
@@ -3552,16 +3605,12 @@ NSC_VerifyInit(CK_SESSION_HANDLE hSession,
context->verify = (SFTKVerify)sftk_RSACheckSignRaw;
finish_rsa:
if (key_type != CKK_RSA) {
- if (info)
- PORT_Free(info);
crv = CKR_KEY_TYPE_INCONSISTENT;
break;
}
context->rsa = PR_TRUE;
pubKey = sftk_GetPubKey(key, CKK_RSA, &crv);
if (pubKey == NULL) {
- if (info)
- PORT_Free(info);
crv = CKR_KEY_TYPE_INCONSISTENT;
break;
}
@@ -3592,19 +3641,20 @@ NSC_VerifyInit(CK_SESSION_HANDLE hSession,
crv = CKR_MECHANISM_PARAM_INVALID;
break;
}
- info = PORT_New(SFTKHashVerifyInfo);
- if (info == NULL) {
+ pinfo = PORT_New(SFTKPSSVerifyInfo);
+ if (pinfo == NULL) {
crv = CKR_HOST_MEMORY;
break;
}
- info->params = pMechanism->pParameter;
- info->key = sftk_GetPubKey(key, CKK_RSA, &crv);
- if (info->key == NULL) {
- PORT_Free(info);
+ pinfo->size = sizeof(SFTKPSSVerifyInfo);
+ pinfo->params = *(CK_RSA_PKCS_PSS_PARAMS *)pMechanism->pParameter;
+ pinfo->key = sftk_GetPubKey(key, CKK_RSA, &crv);
+ if (pinfo->key == NULL) {
+ crv = CKR_KEY_TYPE_INCONSISTENT;
break;
}
- context->cipherInfo = info;
- context->destroy = (SFTKDestroy)sftk_Space;
+ context->cipherInfo = pinfo;
+ context->destroy = (SFTKDestroy)sftk_ZSpace;
context->verify = (SFTKVerify)sftk_RSACheckSignPSS;
break;
@@ -3690,6 +3740,8 @@ NSC_VerifyInit(CK_SESSION_HANDLE hSession,
if (crv != CKR_OK) {
if (info)
PORT_Free(info);
+ if (pinfo)
+ PORT_ZFree(pinfo, pinfo->size);
sftk_FreeContext(context);
sftk_FreeSession(session);
return crv;
@@ -3776,6 +3828,7 @@ NSC_VerifyFinal(CK_SESSION_HANDLE hSession,
if (SECSuccess != (context->verify)(context->cipherInfo, pSignature,
ulSignatureLen, tmpbuf, digestLen))
crv = sftk_MapCryptError(PORT_GetError());
+ PORT_Memset(tmpbuf, 0, sizeof tmpbuf);
} else if (ulSignatureLen != context->macSize) {
/* must be block cipher MACing */
crv = CKR_SIGNATURE_LEN_RANGE;
@@ -4756,6 +4809,7 @@ NSC_GenerateKey(CK_SESSION_HANDLE hSession,
*phKey = key->handle;
}
loser:
+ PORT_Memset(buf, 0, sizeof buf);
sftk_FreeObject(key);
return crv;
}
@@ -5055,7 +5109,7 @@ sftk_PairwiseConsistencyCheck(CK_SESSION_HANDLE hSession, SFTKSlot *slot,
if (isDerivable) {
SFTKAttribute *pubAttribute = NULL;
CK_OBJECT_HANDLE newKey;
- PRBool isFIPS = (slot->slotID == FIPS_SLOT_ID);
+ PRBool isFIPS = sftk_isFIPS(slot->slotID);
CK_RV crv2;
CK_OBJECT_CLASS secret = CKO_SECRET_KEY;
CK_KEY_TYPE generic = CKK_GENERIC_SECRET;
@@ -5141,8 +5195,8 @@ sftk_PairwiseConsistencyCheck(CK_SESSION_HANDLE hSession, SFTKSlot *slot,
crv = CKR_GENERAL_ERROR;
}
done:
- PORT_Free(subPrime.data);
- PORT_Free(prime.data);
+ SECITEM_ZfreeItem(&subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&prime, PR_FALSE);
}
/* clean up before we return */
sftk_FreeAttribute(pubAttribute);
@@ -5296,18 +5350,18 @@ NSC_GenerateKeyPair(CK_SESSION_HANDLE hSession,
bitSize = sftk_GetLengthInBits(pubExp.data, pubExp.len);
if (bitSize < 2) {
crv = CKR_ATTRIBUTE_VALUE_INVALID;
- PORT_Free(pubExp.data);
+ SECITEM_ZfreeItem(&pubExp, PR_FALSE);
break;
}
crv = sftk_AddAttributeType(privateKey, CKA_PUBLIC_EXPONENT,
sftk_item_expand(&pubExp));
if (crv != CKR_OK) {
- PORT_Free(pubExp.data);
+ SECITEM_ZfreeItem(&pubExp, PR_FALSE);
break;
}
rsaPriv = RSA_NewKey(public_modulus_bits, &pubExp);
- PORT_Free(pubExp.data);
+ SECITEM_ZfreeItem(&pubExp, PR_FALSE);
if (rsaPriv == NULL) {
if (PORT_GetError() == SEC_ERROR_LIBRARY_FAILURE) {
sftk_fatalError = PR_TRUE;
@@ -5370,37 +5424,37 @@ NSC_GenerateKeyPair(CK_SESSION_HANDLE hSession,
crv = sftk_Attribute2SSecItem(NULL, &pqgParam.subPrime, publicKey,
CKA_SUBPRIME);
if (crv != CKR_OK) {
- PORT_Free(pqgParam.prime.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
break;
}
crv = sftk_Attribute2SSecItem(NULL, &pqgParam.base, publicKey, CKA_BASE);
if (crv != CKR_OK) {
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
break;
}
crv = sftk_AddAttributeType(privateKey, CKA_PRIME,
sftk_item_expand(&pqgParam.prime));
if (crv != CKR_OK) {
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
break;
}
crv = sftk_AddAttributeType(privateKey, CKA_SUBPRIME,
sftk_item_expand(&pqgParam.subPrime));
if (crv != CKR_OK) {
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
break;
}
crv = sftk_AddAttributeType(privateKey, CKA_BASE,
sftk_item_expand(&pqgParam.base));
if (crv != CKR_OK) {
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
break;
}
@@ -5411,34 +5465,34 @@ NSC_GenerateKeyPair(CK_SESSION_HANDLE hSession,
pqgParam.subPrime.len);
if ((bitSize < DSA_MIN_Q_BITS) || (bitSize > DSA_MAX_Q_BITS)) {
crv = CKR_TEMPLATE_INCOMPLETE;
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
break;
}
bitSize = sftk_GetLengthInBits(pqgParam.prime.data, pqgParam.prime.len);
if ((bitSize < DSA_MIN_P_BITS) || (bitSize > DSA_MAX_P_BITS)) {
crv = CKR_TEMPLATE_INCOMPLETE;
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
break;
}
bitSize = sftk_GetLengthInBits(pqgParam.base.data, pqgParam.base.len);
if ((bitSize < 2) || (bitSize > DSA_MAX_P_BITS)) {
crv = CKR_TEMPLATE_INCOMPLETE;
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
break;
}
/* Generate the key */
rv = DSA_NewKey(&pqgParam, &dsaPriv);
- PORT_Free(pqgParam.prime.data);
- PORT_Free(pqgParam.subPrime.data);
- PORT_Free(pqgParam.base.data);
+ SECITEM_ZfreeItem(&pqgParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.subPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&pqgParam.base, PR_FALSE);
if (rv != SECSuccess) {
if (PORT_GetError() == SEC_ERROR_LIBRARY_FAILURE) {
@@ -5481,41 +5535,41 @@ NSC_GenerateKeyPair(CK_SESSION_HANDLE hSession,
break;
crv = sftk_Attribute2SSecItem(NULL, &dhParam.base, publicKey, CKA_BASE);
if (crv != CKR_OK) {
- PORT_Free(dhParam.prime.data);
+ SECITEM_ZfreeItem(&dhParam.prime, PR_FALSE);
break;
}
crv = sftk_AddAttributeType(privateKey, CKA_PRIME,
sftk_item_expand(&dhParam.prime));
if (crv != CKR_OK) {
- PORT_Free(dhParam.prime.data);
- PORT_Free(dhParam.base.data);
+ SECITEM_ZfreeItem(&dhParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhParam.base, PR_FALSE);
break;
}
crv = sftk_AddAttributeType(privateKey, CKA_BASE,
sftk_item_expand(&dhParam.base));
if (crv != CKR_OK) {
- PORT_Free(dhParam.prime.data);
- PORT_Free(dhParam.base.data);
+ SECITEM_ZfreeItem(&dhParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhParam.base, PR_FALSE);
break;
}
bitSize = sftk_GetLengthInBits(dhParam.prime.data, dhParam.prime.len);
if ((bitSize < DH_MIN_P_BITS) || (bitSize > DH_MAX_P_BITS)) {
crv = CKR_TEMPLATE_INCOMPLETE;
- PORT_Free(dhParam.prime.data);
- PORT_Free(dhParam.base.data);
+ SECITEM_ZfreeItem(&dhParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhParam.base, PR_FALSE);
break;
}
bitSize = sftk_GetLengthInBits(dhParam.base.data, dhParam.base.len);
if ((bitSize < 1) || (bitSize > DH_MAX_P_BITS)) {
crv = CKR_TEMPLATE_INCOMPLETE;
- PORT_Free(dhParam.prime.data);
- PORT_Free(dhParam.base.data);
+ SECITEM_ZfreeItem(&dhParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhParam.base, PR_FALSE);
break;
}
rv = DH_NewKey(&dhParam, &dhPriv);
- PORT_Free(dhParam.prime.data);
- PORT_Free(dhParam.base.data);
+ SECITEM_ZfreeItem(&dhParam.prime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhParam.base, PR_FALSE);
if (rv != SECSuccess) {
if (PORT_GetError() == SEC_ERROR_LIBRARY_FAILURE) {
sftk_fatalError = PR_TRUE;
@@ -5557,13 +5611,13 @@ NSC_GenerateKeyPair(CK_SESSION_HANDLE hSession,
crv = sftk_AddAttributeType(privateKey, CKA_EC_PARAMS,
sftk_item_expand(&ecEncodedParams));
if (crv != CKR_OK) {
- PORT_Free(ecEncodedParams.data);
+ SECITEM_ZfreeItem(&ecEncodedParams, PR_FALSE);
break;
}
/* Decode ec params before calling EC_NewKey */
rv = EC_DecodeParams(&ecEncodedParams, &ecParams);
- PORT_Free(ecEncodedParams.data);
+ SECITEM_ZfreeItem(&ecEncodedParams, PR_FALSE);
if (rv != SECSuccess) {
crv = sftk_MapCryptError(PORT_GetError());
break;
@@ -5594,7 +5648,7 @@ NSC_GenerateKeyPair(CK_SESSION_HANDLE hSession,
}
crv = sftk_AddAttributeType(publicKey, CKA_EC_POINT,
sftk_item_expand(pubValue));
- SECITEM_FreeItem(pubValue, PR_TRUE);
+ SECITEM_ZfreeItem(pubValue, PR_TRUE);
}
if (crv != CKR_OK)
goto ecgn_done;
@@ -6865,6 +6919,7 @@ sftk_DeriveEncrypt(SFTKCipher encrypt, void *cipherInfo,
}
crv = sftk_forceAttribute(key, CKA_VALUE, tmpdata, keySize);
+ PORT_Memset(tmpdata, 0, sizeof tmpdata);
return crv;
}
@@ -7127,7 +7182,7 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
if (key == NULL) {
return CKR_HOST_MEMORY;
}
- isFIPS = (slot->slotID == FIPS_SLOT_ID);
+ isFIPS = sftk_isFIPS(slot->slotID);
/*
* load the template values into the object
@@ -7358,11 +7413,6 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
ssl3_master = (CK_SSL3_MASTER_KEY_DERIVE_PARAMS *)
pMechanism->pParameter;
- PORT_Memcpy(crsrdata,
- ssl3_master->RandomInfo.pClientRandom, SSL3_RANDOM_LENGTH);
- PORT_Memcpy(crsrdata + SSL3_RANDOM_LENGTH,
- ssl3_master->RandomInfo.pServerRandom, SSL3_RANDOM_LENGTH);
-
if (ssl3_master->pVersion) {
SFTKSessionObject *sessKey = sftk_narrowToSessionObject(key);
rsa_pms = (SSL3RSAPreMasterSecret *)att->attrib.pValue;
@@ -7383,6 +7433,10 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
crv = CKR_MECHANISM_PARAM_INVALID;
break;
}
+ PORT_Memcpy(crsrdata,
+ ssl3_master->RandomInfo.pClientRandom, SSL3_RANDOM_LENGTH);
+ PORT_Memcpy(crsrdata + SSL3_RANDOM_LENGTH,
+ ssl3_master->RandomInfo.pServerRandom, SSL3_RANDOM_LENGTH);
if (isTLS) {
SECStatus status;
@@ -7404,6 +7458,7 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
status = TLS_PRF(&pms, "master secret", &crsr, &master, isFIPS);
}
if (status != SECSuccess) {
+ PORT_Memset(crsrdata, 0, sizeof crsrdata);
crv = CKR_FUNCTION_FAILED;
break;
}
@@ -7411,11 +7466,13 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
/* now allocate the hash contexts */
md5 = MD5_NewContext();
if (md5 == NULL) {
+ PORT_Memset(crsrdata, 0, sizeof crsrdata);
crv = CKR_HOST_MEMORY;
break;
}
sha = SHA1_NewContext();
if (sha == NULL) {
+ PORT_Memset(crsrdata, 0, sizeof crsrdata);
PORT_Free(md5);
crv = CKR_HOST_MEMORY;
break;
@@ -7438,10 +7495,13 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
}
PORT_Free(md5);
PORT_Free(sha);
+ PORT_Memset(crsrdata, 0, sizeof crsrdata);
+ PORT_Memset(sha_out, 0, sizeof sha_out);
}
/* store the results */
crv = sftk_forceAttribute(key, CKA_VALUE, key_block, SSL3_MASTER_SECRET_LENGTH);
+ PORT_Memset(key_block, 0, sizeof key_block);
if (crv != CKR_OK)
break;
keyType = CKK_GENERIC_SECRET;
@@ -7560,6 +7620,7 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
/* Store the results */
crv = sftk_forceAttribute(key, CKA_VALUE, key_block,
SSL3_MASTER_SECRET_LENGTH);
+ PORT_Memset(key_block, 0, sizeof key_block);
break;
}
@@ -7572,7 +7633,6 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
CK_ULONG effKeySize;
unsigned int block_needed;
unsigned char srcrdata[SSL3_RANDOM_LENGTH * 2];
- unsigned char crsrdata[SSL3_RANDOM_LENGTH * 2];
if (mechanism == CKM_TLS12_KEY_AND_MAC_DERIVE) {
if (BAD_PARAM_CAST(pMechanism, sizeof(CK_TLS12_KEY_MAT_PARAMS))) {
@@ -7636,11 +7696,6 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
PORT_Memcpy(srcrdata + SSL3_RANDOM_LENGTH,
ssl3_keys->RandomInfo.pClientRandom, SSL3_RANDOM_LENGTH);
- PORT_Memcpy(crsrdata,
- ssl3_keys->RandomInfo.pClientRandom, SSL3_RANDOM_LENGTH);
- PORT_Memcpy(crsrdata + SSL3_RANDOM_LENGTH,
- ssl3_keys->RandomInfo.pServerRandom, SSL3_RANDOM_LENGTH);
-
/*
* clear out our returned keys so we can recover on failure
*/
@@ -7664,6 +7719,7 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
if (ssl3_keys->bIsExport) {
MD5_DestroyContext(md5, PR_TRUE);
SHA1_DestroyContext(sha, PR_TRUE);
+ PORT_Memset(srcrdata, 0, sizeof srcrdata);
crv = CKR_MECHANISM_PARAM_INVALID;
break;
}
@@ -7727,6 +7783,7 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
PORT_Assert(outLen == MD5_LENGTH);
block_bytes += outLen;
}
+ PORT_Memset(sha_out, 0, sizeof sha_out);
}
/*
@@ -7805,6 +7862,8 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
crv = CKR_FUNCTION_FAILED;
sftk_freeSSLKeys(hSession, ssl3_keys_out);
}
+ PORT_Memset(srcrdata, 0, sizeof srcrdata);
+ PORT_Memset(key_block, 0, sizeof key_block);
MD5_DestroyContext(md5, PR_TRUE);
SHA1_DestroyContext(sha, PR_TRUE);
sftk_FreeObject(key);
@@ -8230,83 +8289,27 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
MD2_DestroyContext(md2, PR_TRUE);
crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
- case CKM_MD5_KEY_DERIVATION:
- if (keySize == 0)
- keySize = MD5_LENGTH;
- if (keySize > MD5_LENGTH) {
- crv = CKR_TEMPLATE_INCONSISTENT;
- break;
- }
- MD5_HashBuf(key_block, (const unsigned char *)att->attrib.pValue,
- att->attrib.ulValueLen);
-
- crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
- case CKM_SHA1_KEY_DERIVATION:
- if (keySize == 0)
- keySize = SHA1_LENGTH;
- if (keySize > SHA1_LENGTH) {
- crv = CKR_TEMPLATE_INCONSISTENT;
- break;
- }
- SHA1_HashBuf(key_block, (const unsigned char *)att->attrib.pValue,
- att->attrib.ulValueLen);
-
- crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
-
- case CKM_SHA224_KEY_DERIVATION:
- if (keySize == 0)
- keySize = SHA224_LENGTH;
- if (keySize > SHA224_LENGTH) {
- crv = CKR_TEMPLATE_INCONSISTENT;
- break;
- }
- SHA224_HashBuf(key_block, (const unsigned char *)att->attrib.pValue,
- att->attrib.ulValueLen);
-
- crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
-
- case CKM_SHA256_KEY_DERIVATION:
- if (keySize == 0)
- keySize = SHA256_LENGTH;
- if (keySize > SHA256_LENGTH) {
- crv = CKR_TEMPLATE_INCONSISTENT;
- break;
- }
- SHA256_HashBuf(key_block, (const unsigned char *)att->attrib.pValue,
- att->attrib.ulValueLen);
-
- crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
-
- case CKM_SHA384_KEY_DERIVATION:
- if (keySize == 0)
- keySize = SHA384_LENGTH;
- if (keySize > SHA384_LENGTH) {
- crv = CKR_TEMPLATE_INCONSISTENT;
- break;
- }
- SHA384_HashBuf(key_block, (const unsigned char *)att->attrib.pValue,
- att->attrib.ulValueLen);
-
- crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
-
- case CKM_SHA512_KEY_DERIVATION:
- if (keySize == 0)
- keySize = SHA512_LENGTH;
- if (keySize > SHA512_LENGTH) {
- crv = CKR_TEMPLATE_INCONSISTENT;
- break;
- }
- SHA512_HashBuf(key_block, (const unsigned char *)att->attrib.pValue,
- att->attrib.ulValueLen);
-
- crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize);
- break;
+ PORT_Memset(key_block, 0, MD2_LENGTH);
+ break;
+#define DERIVE_KEY_HASH(hash) \
+ case CKM_##hash##_KEY_DERIVATION: \
+ if (keySize == 0) \
+ keySize = hash##_LENGTH; \
+ if (keySize > hash##_LENGTH) { \
+ crv = CKR_TEMPLATE_INCONSISTENT; \
+ break; \
+ } \
+ hash##_HashBuf(key_block, (const unsigned char *)att->attrib.pValue, \
+ att->attrib.ulValueLen); \
+ crv = sftk_forceAttribute(key, CKA_VALUE, key_block, keySize); \
+ PORT_Memset(key_block, 0, hash##_LENGTH); \
+ break;
+ DERIVE_KEY_HASH(MD5)
+ DERIVE_KEY_HASH(SHA1)
+ DERIVE_KEY_HASH(SHA224)
+ DERIVE_KEY_HASH(SHA256)
+ DERIVE_KEY_HASH(SHA384)
+ DERIVE_KEY_HASH(SHA512)
case CKM_DH_PKCS_DERIVE: {
SECItem derived, dhPublic;
@@ -8350,22 +8353,22 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
/* either p or q was even and therefore not prime,
* we can stop processing here and fail now */
crv = CKR_ARGUMENTS_BAD;
- PORT_Free(dhPrime.data);
- PORT_Free(dhSubPrime.data);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhSubPrime, PR_FALSE);
break;
}
/* first make sure the primes are really prime */
if (!KEA_PrimeCheck(&dhPrime)) {
crv = CKR_ARGUMENTS_BAD;
- PORT_Free(dhPrime.data);
- PORT_Free(dhSubPrime.data);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhSubPrime, PR_FALSE);
break;
}
if (!KEA_PrimeCheck(&dhSubPrime)) {
crv = CKR_ARGUMENTS_BAD;
- PORT_Free(dhPrime.data);
- PORT_Free(dhSubPrime.data);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhSubPrime, PR_FALSE);
break;
}
if (isFIPS || !isSafe) {
@@ -8377,8 +8380,8 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
* we receive the subprime value */
if (!KEA_Verify(&dhPublic, &dhPrime, &dhSubPrime)) {
crv = CKR_ARGUMENTS_BAD;
- PORT_Free(dhPrime.data);
- PORT_Free(dhSubPrime.data);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhSubPrime, PR_FALSE);
break;
}
}
@@ -8386,29 +8389,29 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
/* In FIPS mode we only accept approved primes, or
* primes with the full subprime value */
crv = CKR_ARGUMENTS_BAD;
- PORT_Free(dhPrime.data);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
break;
}
/* checks are complete, no need for the subPrime any longer */
- PORT_Free(dhSubPrime.data);
+ SECITEM_ZfreeItem(&dhSubPrime, PR_FALSE);
}
/* now that the prime is validated, get the private value */
crv = sftk_Attribute2SecItem(NULL, &dhValue, sourceKey, CKA_VALUE);
if (crv != CKR_OK) {
- PORT_Free(dhPrime.data);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
break;
}
/* calculate private value - oct */
rv = DH_Derive(&dhPublic, &dhPrime, &dhValue, &derived, keySize);
- PORT_Free(dhPrime.data);
- PORT_ZFree(dhValue.data, dhValue.len);
+ SECITEM_ZfreeItem(&dhPrime, PR_FALSE);
+ SECITEM_ZfreeItem(&dhValue, PR_FALSE);
if (rv == SECSuccess) {
sftk_forceAttribute(key, CKA_VALUE, derived.data, derived.len);
- PORT_ZFree(derived.data, derived.len);
+ SECITEM_ZfreeItem(&derived, PR_FALSE);
crv = CKR_OK;
} else
crv = CKR_HOST_MEMORY;
@@ -8475,7 +8478,7 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
rv = ECDH_Derive(&ecPoint, &privKey->u.ec.ecParams, &ecScalar,
withCofactor, &tmp);
- PORT_ZFree(ecScalar.data, ecScalar.len);
+ SECITEM_ZfreeItem(&ecScalar, PR_FALSE);
ecScalar.data = NULL;
if (privKey != sourceKey->objectInfo) {
nsslowkey_DestroyPrivateKey(privKey);
@@ -8547,11 +8550,11 @@ NSC_DeriveKey(CK_SESSION_HANDLE hSession,
ec_loser:
crv = CKR_ARGUMENTS_BAD;
- PORT_Free(ecScalar.data);
+ SECITEM_ZfreeItem(&ecScalar, PR_FALSE);
if (privKey != sourceKey->objectInfo)
nsslowkey_DestroyPrivateKey(privKey);
if (arena) {
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
}
break;
}
diff --git a/lib/softoken/pkcs11i.h b/lib/softoken/pkcs11i.h
index 2aabb37e4..26efe158b 100644
--- a/lib/softoken/pkcs11i.h
+++ b/lib/softoken/pkcs11i.h
@@ -105,8 +105,9 @@ typedef struct SFTKSessionContextStr SFTKSessionContext;
typedef struct SFTKSearchResultsStr SFTKSearchResults;
typedef struct SFTKHashVerifyInfoStr SFTKHashVerifyInfo;
typedef struct SFTKHashSignInfoStr SFTKHashSignInfo;
-typedef struct SFTKOAEPEncryptInfoStr SFTKOAEPEncryptInfo;
-typedef struct SFTKOAEPDecryptInfoStr SFTKOAEPDecryptInfo;
+typedef struct SFTKOAEPInfoStr SFTKOAEPInfo;
+typedef struct SFTKPSSSignInfoStr SFTKPSSSignInfo;
+typedef struct SFTKPSSVerifyInfoStr SFTKPSSVerifyInfo;
typedef struct SFTKSSLMACInfoStr SFTKSSLMACInfo;
typedef struct SFTKChaCha20Poly1305InfoStr SFTKChaCha20Poly1305Info;
typedef struct SFTKChaCha20CtrInfoStr SFTKChaCha20CtrInfo;
@@ -388,21 +389,33 @@ struct SFTKHashSignInfoStr {
NSSLOWKEYPrivateKey *key;
};
-/**
- * Contexts for RSA-OAEP
- */
-struct SFTKOAEPEncryptInfoStr {
- CK_RSA_PKCS_OAEP_PARAMS *params;
+struct SFTKPSSVerifyInfoStr {
+ size_t size; /* must be first */
+ CK_RSA_PKCS_PSS_PARAMS params;
NSSLOWKEYPublicKey *key;
};
-struct SFTKOAEPDecryptInfoStr {
- CK_RSA_PKCS_OAEP_PARAMS *params;
+struct SFTKPSSSignInfoStr {
+ size_t size; /* must be first */
+ CK_RSA_PKCS_PSS_PARAMS params;
NSSLOWKEYPrivateKey *key;
};
+/**
+ * Contexts for RSA-OAEP
+ */
+struct SFTKOAEPInfoStr {
+ CK_RSA_PKCS_OAEP_PARAMS params;
+ PRBool isEncrypt;
+ union {
+ NSSLOWKEYPublicKey *pub;
+ NSSLOWKEYPrivateKey *priv;
+ } key;
+};
+
/* context for the Final SSLMAC message */
struct SFTKSSLMACInfoStr {
+ size_t size; /* must be first */
void *hashContext;
SFTKBegin begin;
SFTKHash update;
@@ -481,6 +494,8 @@ struct SFTKItemTemplateStr {
/* slot helper macros */
#define sftk_SlotFromSession(sp) ((sp)->slot)
#define sftk_isToken(id) (((id)&SFTK_TOKEN_MASK) == SFTK_TOKEN_MAGIC)
+#define sftk_isFIPS(id) \
+ (((id) == FIPS_SLOT_ID) || ((id) >= SFTK_MIN_FIPS_USER_SLOT_ID))
/* the session hash multiplier (see bug 201081) */
#define SHMULTIPLIER 1791398085
diff --git a/lib/softoken/pkcs11u.c b/lib/softoken/pkcs11u.c
index 7d969a1bc..4b314f4b8 100644
--- a/lib/softoken/pkcs11u.c
+++ b/lib/softoken/pkcs11u.c
@@ -155,16 +155,19 @@ sftk_NewAttribute(SFTKObject *object,
static void
sftk_DestroyAttribute(SFTKAttribute *attribute)
{
- if (attribute->freeData) {
- if (attribute->attrib.pValue) {
- /* clear out the data in the attribute value... it may have been
- * sensitive data */
- PORT_Memset(attribute->attrib.pValue, 0,
- attribute->attrib.ulValueLen);
+ if (attribute->attrib.pValue) {
+ /* clear out the data in the attribute value... it may have been
+ * sensitive data */
+ PORT_Memset(attribute->attrib.pValue, 0, attribute->attrib.ulValueLen);
+ if (attribute->freeData) {
+ PORT_Free(attribute->attrib.pValue);
+ attribute->attrib.pValue = NULL;
+ attribute->freeData = PR_FALSE;
}
- PORT_Free(attribute->attrib.pValue);
}
- PORT_Free(attribute);
+ if (attribute->freeAttr) {
+ PORT_Free(attribute);
+ }
}
/*
@@ -864,7 +867,7 @@ sftk_DeleteAttributeType(SFTKObject *object, CK_ATTRIBUTE_TYPE type)
if (attribute == NULL)
return;
sftk_DeleteAttribute(object, attribute);
- sftk_FreeAttribute(attribute);
+ sftk_DestroyAttribute(attribute);
}
CK_RV
diff --git a/lib/softoken/sftkdb.c b/lib/softoken/sftkdb.c
index 5c4608a9b..cfa056396 100644
--- a/lib/softoken/sftkdb.c
+++ b/lib/softoken/sftkdb.c
@@ -162,7 +162,7 @@ sftk_SDBULong2ULong(unsigned char *data)
*/
static CK_ATTRIBUTE *
sftkdb_fixupTemplateIn(const CK_ATTRIBUTE *template, int count,
- unsigned char **dataOut)
+ unsigned char **dataOut, int *dataOutSize)
{
int i;
int ulongCount = 0;
@@ -170,6 +170,7 @@ sftkdb_fixupTemplateIn(const CK_ATTRIBUTE *template, int count,
CK_ATTRIBUTE *ntemplate;
*dataOut = NULL;
+ *dataOutSize = 0;
/* first count the number of CK_ULONG attributes */
for (i = 0; i < count; i++) {
@@ -201,6 +202,7 @@ sftkdb_fixupTemplateIn(const CK_ATTRIBUTE *template, int count,
return NULL;
}
*dataOut = data;
+ *dataOutSize = SDB_ULONG_SIZE * ulongCount;
/* copy the old template, fixup the actual ulongs */
for (i = 0; i < count; i++) {
ntemplate[i] = template[i];
@@ -400,7 +402,7 @@ sftkdb_fixupTemplateOut(CK_ATTRIBUTE *template, CK_OBJECT_HANDLE objectID,
}
PORT_Assert(template[i].ulValueLen >= plainText->len);
if (template[i].ulValueLen < plainText->len) {
- SECITEM_FreeItem(plainText, PR_TRUE);
+ SECITEM_ZfreeItem(plainText, PR_TRUE);
PORT_Memset(template[i].pValue, 0, template[i].ulValueLen);
template[i].ulValueLen = -1;
crv = CKR_GENERAL_ERROR;
@@ -410,7 +412,7 @@ sftkdb_fixupTemplateOut(CK_ATTRIBUTE *template, CK_OBJECT_HANDLE objectID,
/* copy the plain text back into the template */
PORT_Memcpy(template[i].pValue, plainText->data, plainText->len);
template[i].ulValueLen = plainText->len;
- SECITEM_FreeItem(plainText, PR_TRUE);
+ SECITEM_ZfreeItem(plainText, PR_TRUE);
}
/* make sure signed attributes are valid */
if (checkSig && sftkdb_isAuthenticatedAttribute(ntemplate[i].type)) {
@@ -1293,7 +1295,7 @@ loser:
}
if (arena) {
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
}
if (crv == CKR_OK) {
*objectID |= (handle->type | SFTK_TOKEN_TYPE);
@@ -1308,6 +1310,7 @@ sftkdb_FindObjectsInit(SFTKDBHandle *handle, const CK_ATTRIBUTE *template,
unsigned char *data = NULL;
CK_ATTRIBUTE *ntemplate = NULL;
CK_RV crv;
+ int dataSize;
SDB *db;
if (handle == NULL) {
@@ -1316,7 +1319,7 @@ sftkdb_FindObjectsInit(SFTKDBHandle *handle, const CK_ATTRIBUTE *template,
db = SFTK_GET_SDB(handle);
if (count != 0) {
- ntemplate = sftkdb_fixupTemplateIn(template, count, &data);
+ ntemplate = sftkdb_fixupTemplateIn(template, count, &data, &dataSize);
if (ntemplate == NULL) {
return CKR_HOST_MEMORY;
}
@@ -1326,7 +1329,7 @@ sftkdb_FindObjectsInit(SFTKDBHandle *handle, const CK_ATTRIBUTE *template,
count, find);
if (data) {
PORT_Free(ntemplate);
- PORT_Free(data);
+ PORT_ZFree(data, dataSize);
}
return crv;
}
@@ -1373,6 +1376,7 @@ sftkdb_GetAttributeValue(SFTKDBHandle *handle, CK_OBJECT_HANDLE objectID,
CK_RV crv, crv2;
CK_ATTRIBUTE *ntemplate;
unsigned char *data = NULL;
+ int dataSize = 0;
SDB *db;
if (handle == NULL) {
@@ -1413,7 +1417,7 @@ sftkdb_GetAttributeValue(SFTKDBHandle *handle, CK_OBJECT_HANDLE objectID,
if (count == 0) {
return CKR_OK;
}
- ntemplate = sftkdb_fixupTemplateIn(template, count, &data);
+ ntemplate = sftkdb_fixupTemplateIn(template, count, &data, &dataSize);
if (ntemplate == NULL) {
return CKR_HOST_MEMORY;
}
@@ -1426,7 +1430,7 @@ sftkdb_GetAttributeValue(SFTKDBHandle *handle, CK_OBJECT_HANDLE objectID,
crv = crv2;
if (data) {
PORT_Free(ntemplate);
- PORT_Free(data);
+ PORT_ZFree(data, dataSize);
}
return crv;
}
@@ -1442,6 +1446,7 @@ sftkdb_SetAttributeValue(SFTKDBHandle *handle, SFTKObject *object,
CK_RV crv = CKR_OK;
CK_OBJECT_HANDLE objectID = (object->handle & SFTK_OBJ_ID_MASK);
PRBool inTransaction = PR_FALSE;
+ int dataSize;
if (handle == NULL) {
return CKR_TOKEN_WRITE_PROTECTED;
@@ -1463,7 +1468,7 @@ sftkdb_SetAttributeValue(SFTKDBHandle *handle, SFTKObject *object,
return CKR_USER_NOT_LOGGED_IN;
}
- ntemplate = sftkdb_fixupTemplateIn(template, count, &data);
+ ntemplate = sftkdb_fixupTemplateIn(template, count, &data, &dataSize);
if (ntemplate == NULL) {
return CKR_HOST_MEMORY;
}
@@ -1498,7 +1503,7 @@ loser:
}
if (data) {
PORT_Free(ntemplate);
- PORT_Free(data);
+ PORT_ZFree(data, dataSize);
}
if (arena) {
PORT_FreeArena(arena, PR_FALSE);
@@ -1602,13 +1607,13 @@ sftkdb_CloseDB(SFTKDBHandle *handle)
(*handle->db->sdb_Close)(handle->db);
}
if (handle->passwordKey.data) {
- PORT_ZFree(handle->passwordKey.data, handle->passwordKey.len);
+ SECITEM_ZfreeItem(&handle->passwordKey, PR_FALSE);
}
if (handle->passwordLock) {
SKIP_AFTER_FORK(PZ_DestroyLock(handle->passwordLock));
}
if (handle->updatePasswordKey) {
- SECITEM_FreeItem(handle->updatePasswordKey, PR_TRUE);
+ SECITEM_ZfreeItem(handle->updatePasswordKey, PR_TRUE);
}
if (handle->updateID) {
PORT_Free(handle->updateID);
@@ -2690,6 +2695,10 @@ sftkdb_ResetKeyDB(SFTKDBHandle *handle)
/* set error */
return SECFailure;
}
+ if (handle->passwordKey.data) {
+ SECITEM_ZfreeItem(&handle->passwordKey, PR_FALSE);
+ handle->passwordKey.data = NULL;
+ }
return SECSuccess;
}
diff --git a/lib/softoken/sftkhmac.c b/lib/softoken/sftkhmac.c
index b9ee7d054..1b38b06f9 100644
--- a/lib/softoken/sftkhmac.c
+++ b/lib/softoken/sftkhmac.c
@@ -69,6 +69,7 @@ SetupMAC(CK_MECHANISM_PTR mech, SFTKObject *key)
ctx = PORT_Alloc(sizeof(sftk_MACConstantTimeCtx));
if (!ctx) {
+ PORT_Memset(secret, 0, secretLength);
return NULL;
}
@@ -76,6 +77,7 @@ SetupMAC(CK_MECHANISM_PTR mech, SFTKObject *key)
ctx->secretLength = secretLength;
ctx->hash = HASH_GetRawHashObject(alg);
ctx->totalLength = params->ulBodyTotalLen;
+ PORT_Memset(secret, 0, secretLength);
return ctx;
}
@@ -188,7 +190,7 @@ sftk_MACConstantTime_EndHash(void *pctx, void *out, unsigned int *outLength,
void
sftk_MACConstantTime_DestroyContext(void *pctx, PRBool free)
{
- PORT_Free(pctx);
+ PORT_ZFree(pctx, sizeof(sftk_MACConstantTimeCtx));
}
CK_RV
@@ -217,7 +219,7 @@ CK_RV
sftk_MAC_Init(sftk_MACCtx *ctx, CK_MECHANISM_TYPE mech, SFTKObject *key)
{
SFTKAttribute *keyval = NULL;
- PRBool isFIPS = (key->slot->slotID == FIPS_SLOT_ID);
+ PRBool isFIPS = sftk_isFIPS(key->slot->slotID);
CK_RV ret = CKR_OK;
/* Find the actual value of the key. */
diff --git a/lib/softoken/sftkike.c b/lib/softoken/sftkike.c
index 049675ff8..2183add69 100644
--- a/lib/softoken/sftkike.c
+++ b/lib/softoken/sftkike.c
@@ -465,7 +465,7 @@ sftk_ike_prf(CK_SESSION_HANDLE hSession, const SFTKAttribute *inKey,
SFTKObject *newKeyObj = NULL;
unsigned char outKeyData[HASH_LENGTH_MAX];
unsigned char *newInKey = NULL;
- unsigned int newInKeySize;
+ unsigned int newInKeySize = 0;
unsigned int macSize;
CK_RV crv = CKR_OK;
prfContext context;
@@ -545,7 +545,7 @@ sftk_ike_prf(CK_SESSION_HANDLE hSession, const SFTKAttribute *inKey,
crv = sftk_forceAttribute(outKey, CKA_VALUE, outKeyData, macSize);
fail:
if (newInKey) {
- PORT_Free(newInKey);
+ PORT_ZFree(newInKey, newInKeySize);
}
if (newKeyValue) {
sftk_FreeAttribute(newKeyValue);
diff --git a/lib/softoken/sftkpwd.c b/lib/softoken/sftkpwd.c
index b41cf9dab..e0ff76f08 100644
--- a/lib/softoken/sftkpwd.c
+++ b/lib/softoken/sftkpwd.c
@@ -252,7 +252,7 @@ sftkdb_encodeCipherText(PLArenaPool *arena, sftkCipherValue *cipherValue,
loser:
if (localArena) {
- PORT_FreeArena(localArena, PR_FALSE);
+ PORT_FreeArena(localArena, PR_TRUE);
}
return rv;
@@ -419,7 +419,7 @@ sftkdb_EncryptAttribute(PLArenaPool *arena, SFTKDBHandle *handle, SDB *db,
loser:
if ((arena == NULL) && signature) {
- SECITEM_FreeItem(cipher, PR_TRUE);
+ SECITEM_ZfreeItem(signature, PR_TRUE);
}
if (cipher) {
SECITEM_FreeItem(cipher, PR_TRUE);
@@ -486,7 +486,7 @@ loser:
HMAC_Destroy(hashCx, PR_TRUE);
}
if (key) {
- SECITEM_FreeItem(key, PR_TRUE);
+ SECITEM_ZfreeItem(key, PR_TRUE);
}
return rv;
}
@@ -526,11 +526,12 @@ sftkdb_VerifyAttribute(SFTKDBHandle *handle,
}
loser:
+ PORT_Memset(signData, 0, sizeof signData);
if (signValue.param) {
nsspkcs5_DestroyPBEParameter(signValue.param);
}
if (signValue.arena) {
- PORT_FreeArena(signValue.arena, PR_FALSE);
+ PORT_FreeArena(signValue.arena, PR_TRUE);
}
return rv;
}
@@ -608,6 +609,7 @@ sftkdb_SignAttribute(PLArenaPool *arena, SFTKDBHandle *keyDB, SDB *db,
}
loser:
+ PORT_Memset(signData, 0, sizeof signData);
if (param) {
nsspkcs5_DestroyPBEParameter(param);
}
@@ -1079,7 +1081,7 @@ sftkdb_finishPasswordCheck(SFTKDBHandle *keydb, SECItem *key, const char *pw,
done:
if (result) {
- SECITEM_FreeItem(result, PR_TRUE);
+ SECITEM_ZfreeItem(result, PR_TRUE);
}
return rv;
}
@@ -1273,8 +1275,7 @@ sftk_convertAttributes(SFTKDBHandle *handle, CK_OBJECT_HANDLE id,
}
/* free up our mess */
- /* NOTE: at this point we know we've cleared out any unencrypted data */
- PORT_FreeArena(arena, PR_FALSE);
+ PORT_FreeArena(arena, PR_TRUE);
return CKR_OK;
loser:
diff --git a/lib/softoken/tlsprf.c b/lib/softoken/tlsprf.c
index b96733b1f..042cf194f 100644
--- a/lib/softoken/tlsprf.c
+++ b/lib/softoken/tlsprf.c
@@ -174,7 +174,7 @@ sftk_TLSPRFInit(SFTKSessionContext *context,
prf_cx->cxDataLen = 0;
prf_cx->cxBufSize = blockSize - offsetof(TLSPRFContext, cxBuf);
prf_cx->cxRv = SECSuccess;
- prf_cx->cxIsFIPS = (key->slot->slotID == FIPS_SLOT_ID);
+ prf_cx->cxIsFIPS = sftk_isFIPS(key->slot->slotID);
prf_cx->cxBufPtr = prf_cx->cxBuf;
prf_cx->cxHashAlg = hash_alg;
prf_cx->cxOutLen = out_len;
diff --git a/lib/util/secalgid.c b/lib/util/secalgid.c
index 718bb03ea..b3e8e89db 100644
--- a/lib/util/secalgid.c
+++ b/lib/util/secalgid.c
@@ -110,7 +110,7 @@ SECOID_CopyAlgorithmID(PLArenaPool *arena, SECAlgorithmID *to,
void
SECOID_DestroyAlgorithmID(SECAlgorithmID *algid, PRBool freeit)
{
- SECITEM_FreeItem(&algid->parameters, PR_FALSE);
+ SECITEM_ZfreeItem(&algid->parameters, PR_FALSE);
SECITEM_FreeItem(&algid->algorithm, PR_FALSE);
if (freeit == PR_TRUE)
PORT_Free(algid);
diff --git a/lib/util/secdig.c b/lib/util/secdig.c
index f4deec54b..28377c2f8 100644
--- a/lib/util/secdig.c
+++ b/lib/util/secdig.c
@@ -135,7 +135,7 @@ void
SGN_DestroyDigestInfo(SGNDigestInfo *di)
{
if (di && di->arena) {
- PORT_FreeArena(di->arena, PR_FALSE);
+ PORT_FreeArena(di->arena, PR_TRUE);
}
return;