diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-19 01:13:27 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-19 01:13:27 +0000 |
commit | 40a355a42d4a9444dc753c04c6608dade2f06a23 (patch) | |
tree | 871fc667d2de662f171103ce5ec067014ef85e61 /security/nss/lib/cryptohi | |
parent | Adding upstream version 124.0.1. (diff) | |
download | firefox-40a355a42d4a9444dc753c04c6608dade2f06a23.tar.xz firefox-40a355a42d4a9444dc753c04c6608dade2f06a23.zip |
Adding upstream version 125.0.1.upstream/125.0.1
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'security/nss/lib/cryptohi')
-rw-r--r-- | security/nss/lib/cryptohi/keythi.h | 1 | ||||
-rw-r--r-- | security/nss/lib/cryptohi/seckey.c | 129 | ||||
-rw-r--r-- | security/nss/lib/cryptohi/secvfy.c | 2 |
3 files changed, 126 insertions, 6 deletions
diff --git a/security/nss/lib/cryptohi/keythi.h b/security/nss/lib/cryptohi/keythi.h index 1dd8a557c5..086d83ae6b 100644 --- a/security/nss/lib/cryptohi/keythi.h +++ b/security/nss/lib/cryptohi/keythi.h @@ -36,6 +36,7 @@ typedef enum { rsaPssKey = 7, rsaOaepKey = 8, kyberKey = 9, + edKey = 10, } KeyType; /* diff --git a/security/nss/lib/cryptohi/seckey.c b/security/nss/lib/cryptohi/seckey.c index 1762c1a143..1a68104978 100644 --- a/security/nss/lib/cryptohi/seckey.c +++ b/security/nss/lib/cryptohi/seckey.c @@ -235,6 +235,33 @@ SECKEY_CreateECPrivateKey(SECKEYECParams *param, SECKEYPublicKey **pubk, void *c return (privk); } +SECKEYPrivateKey * +SECKEY_CreateEDPrivateKey(SECKEYECParams *param, SECKEYPublicKey **pubk, void *cx) +{ + SECKEYPrivateKey *privk; + PK11SlotInfo *slot = PK11_GetBestSlot(CKM_EC_EDWARDS_KEY_PAIR_GEN, cx); + if (!slot) { + return NULL; + } + + privk = PK11_GenerateKeyPairWithOpFlags(slot, CKM_EC_EDWARDS_KEY_PAIR_GEN, + param, pubk, + PK11_ATTR_SESSION | + PK11_ATTR_INSENSITIVE | + PK11_ATTR_PUBLIC, + CKF_SIGN, CKF_SIGN, cx); + if (!privk) + privk = PK11_GenerateKeyPairWithOpFlags(slot, CKM_EC_EDWARDS_KEY_PAIR_GEN, + param, pubk, + PK11_ATTR_SESSION | + PK11_ATTR_SENSITIVE | + PK11_ATTR_PRIVATE, + CKF_SIGN, CKF_SIGN, cx); + + PK11_FreeSlot(slot); + return (privk); +} + void SECKEY_DestroyPrivateKey(SECKEYPrivateKey *privk) { @@ -329,7 +356,7 @@ seckey_UpdateCertPQGChain(CERTCertificate *subjectCert, int count) * * Question: do we really need to do this for EC keys. They don't have * PQG parameters, but they do have parameters. The question is does - * the child cert inherit thost parameters for EC from the parent, or + * the child cert inherit those parameters for EC from the parent, or * do we always include those parameters in each cert. */ @@ -339,6 +366,7 @@ seckey_UpdateCertPQGChain(CERTCertificate *subjectCert, int count) (tag != SEC_OID_NIST_DSA_SIGNATURE_WITH_SHA256_DIGEST) && (tag != SEC_OID_BOGUS_DSA_SIGNATURE_WITH_SHA1_DIGEST) && (tag != SEC_OID_SDN702_DSA_SIGNATURE) && + (tag != SEC_OID_ED25519_PUBLIC_KEY) && (tag != SEC_OID_ANSIX962_EC_PUBLIC_KEY)) { return SECSuccess; @@ -383,6 +411,7 @@ seckey_UpdateCertPQGChain(CERTCertificate *subjectCert, int count) (tag != SEC_OID_NIST_DSA_SIGNATURE_WITH_SHA256_DIGEST) && (tag != SEC_OID_BOGUS_DSA_SIGNATURE_WITH_SHA1_DIGEST) && (tag != SEC_OID_SDN702_DSA_SIGNATURE) && + (tag != SEC_OID_ED25519_PUBLIC_KEY) && (tag != SEC_OID_ANSIX962_EC_PUBLIC_KEY)) { rv = SECFailure; goto loser; @@ -521,6 +550,9 @@ seckey_GetKeyType(SECOidTag tag) case SEC_OID_ANSIX962_EC_PUBLIC_KEY: keyType = ecKey; break; + case SEC_OID_ED25519_PUBLIC_KEY: + keyType = edKey; + break; /* accommodate applications that hand us a signature type when they * should be handing us a cipher type */ case SEC_OID_PKCS1_MD5_WITH_RSA_ENCRYPTION: @@ -637,6 +669,37 @@ seckey_ExtractPublicKey(const CERTSubjectPublicKeyInfo *spki) if (rv == SECSuccess) return pubk; break; + case SEC_OID_ED25519_PUBLIC_KEY: + /* A basic consistency check on inputs. */ + if (newOs.len == 0) { + PORT_SetError(SEC_ERROR_INPUT_LEN); + break; + } + + /* Currently supporting only (Pure)Ed25519 .*/ + if (spki->algorithm.parameters.len != 0) { + PORT_SetError(SEC_ERROR_UNSUPPORTED_KEYALG); + break; + } + + pubk->keyType = edKey; + pubk->u.ec.size = 0; + + SECOidData *oidEd25519 = SECOID_FindOIDByTag(SEC_OID_ED25519_PUBLIC_KEY); + + if (!SECITEM_AllocItem(arena, &pubk->u.ec.DEREncodedParams, oidEd25519->oid.len + 2)) { + rv = SECFailure; + break; + } + pubk->u.ec.DEREncodedParams.data[0] = SEC_ASN1_OBJECT_ID; + pubk->u.ec.DEREncodedParams.data[1] = oidEd25519->oid.len; + PORT_Memcpy(pubk->u.ec.DEREncodedParams.data + 2, oidEd25519->oid.data, oidEd25519->oid.len); + + rv = SECITEM_CopyItem(arena, &pubk->u.ec.publicValue, &newOs); + if (rv != SECSuccess) { + break; + } + return pubk; case SEC_OID_ANSIX962_EC_PUBLIC_KEY: /* A basic sanity check on inputs. */ if (spki->algorithm.parameters.len == 0 || newOs.len == 0) { @@ -811,6 +874,7 @@ SECKEY_ECParamsToKeySize(const SECItem *encodedParams) return 571; case SEC_OID_CURVE25519: + case SEC_OID_ED25519_PUBLIC_KEY: return 255; default: @@ -961,6 +1025,7 @@ SECKEY_ECParamsToBasePointOrderLen(const SECItem *encodedParams) return 570; case SEC_OID_CURVE25519: + case SEC_OID_ED25519_PUBLIC_KEY: return 255; default: @@ -1032,6 +1097,7 @@ SECKEY_PublicKeyStrengthInBits(const SECKEYPublicKey *pubk) bitSize = SECKEY_BigIntegerBitLength(&pubk->u.dh.prime); break; case ecKey: + case edKey: bitSize = SECKEY_ECParamsToKeySize(&pubk->u.ec.DEREncodedParams); break; default: @@ -1113,6 +1179,7 @@ SECKEY_SignatureLen(const SECKEYPublicKey *pubk) case dsaKey: return pubk->u.dsa.params.subPrime.len * 2; case ecKey: + case edKey: /* Get the base point order length in bits and adjust */ size = SECKEY_ECParamsToBasePointOrderLen( &pubk->u.ec.DEREncodedParams); @@ -1239,6 +1306,7 @@ SECKEY_CopyPublicKey(const SECKEYPublicKey *pubk) &pubk->u.dh.publicValue); break; case ecKey: + case edKey: copyk->u.ec.size = pubk->u.ec.size; rv = seckey_HasCurveOID(pubk); if (rv != SECSuccess) { @@ -1465,6 +1533,28 @@ SECKEY_ConvertToPublicKey(SECKEYPrivateKey *privk) * overwrite the old value */ pubk->u.ec.publicValue = decodedPoint; } + + pubk->u.ec.encoding = ECPoint_Undefined; + return pubk; + case edKey: + rv = PK11_ReadAttribute(privk->pkcs11Slot, privk->pkcs11ID, + CKA_EC_PARAMS, arena, &pubk->u.ec.DEREncodedParams); + if (rv != SECSuccess) { + break; + } + rv = PK11_ReadAttribute(privk->pkcs11Slot, privk->pkcs11ID, + CKA_EC_POINT, arena, &pubk->u.ec.publicValue); + if (rv != SECSuccess || pubk->u.ec.publicValue.len == 0) { + pubKeyHandle = seckey_FindPublicKeyHandle(privk, pubk); + if (pubKeyHandle == CK_INVALID_HANDLE) { + break; + } + rv = PK11_ReadAttribute(privk->pkcs11Slot, pubKeyHandle, + CKA_EC_POINT, arena, &pubk->u.ec.publicValue); + if (rv != SECSuccess) { + break; + } + } pubk->u.ec.encoding = ECPoint_Undefined; return pubk; default: @@ -1483,6 +1573,7 @@ seckey_CreateSubjectPublicKeyInfo_helper(SECKEYPublicKey *pubk) CERTSubjectPublicKeyInfo *spki; PLArenaPool *arena; SECItem params = { siBuffer, NULL, 0 }; + SECOidTag tag; arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); if (arena == NULL) { @@ -1555,14 +1646,41 @@ seckey_CreateSubjectPublicKeyInfo_helper(SECKEYPublicKey *pubk) case ecKey: rv = SECITEM_CopyItem(arena, ¶ms, &pubk->u.ec.DEREncodedParams); - if (rv != SECSuccess) + if (rv != SECSuccess) { break; + } + tag = SEC_OID_ANSIX962_EC_PUBLIC_KEY; rv = SECOID_SetAlgorithmID(arena, &spki->algorithm, - SEC_OID_ANSIX962_EC_PUBLIC_KEY, + tag, ¶ms); - if (rv != SECSuccess) + if (rv != SECSuccess) { + break; + } + + rv = SECITEM_CopyItem(arena, &spki->subjectPublicKey, + &pubk->u.ec.publicValue); + + if (rv == SECSuccess) { + /* + * The stored value is supposed to be a BIT_STRING, + * so convert the length. + */ + spki->subjectPublicKey.len <<= 3; + /* + * We got a good one; return it. + */ + return spki; + } + break; + case edKey: + tag = SECKEY_GetECCOid(&pubk->u.ec.DEREncodedParams); + rv = SECOID_SetAlgorithmID(arena, &spki->algorithm, + tag, + ¶ms); + if (rv != SECSuccess) { break; + } rv = SECITEM_CopyItem(arena, &spki->subjectPublicKey, &pubk->u.ec.publicValue); @@ -1669,8 +1787,9 @@ SECKEY_DecodeDERSubjectPublicKeyInfo(const SECItem *spkider) rv = SEC_QuickDERDecodeItem(arena, spki, CERT_SubjectPublicKeyInfoTemplate, &newSpkider); } - if (rv == SECSuccess) + if (rv == SECSuccess) { return spki; + } } else { PORT_SetError(SEC_ERROR_NO_MEMORY); } diff --git a/security/nss/lib/cryptohi/secvfy.c b/security/nss/lib/cryptohi/secvfy.c index 8c9dc2d87d..04c755a001 100644 --- a/security/nss/lib/cryptohi/secvfy.c +++ b/security/nss/lib/cryptohi/secvfy.c @@ -306,7 +306,7 @@ sec_GetEncAlgFromSigAlg(SECOidTag sigAlg) * encalg: address of a SECOidTag which will be set with the signing alg. * * Returns: SECSuccess if the algorithm was acceptable, SECFailure if the - * algorithm was not found or was not a signing algorithm. + * algorithm was not found or was not a signing algorithm. */ SECStatus sec_DecodeSigAlg(const SECKEYPublicKey *key, SECOidTag sigAlg, |