static SECStatus crmf_copy_popoprivkey(PLArenaPool *poolp, CRMFPOPOPrivKey *srcPrivKey, CRMFPOPOPrivKey *destPrivKey) { SECStatus rv; destPrivKey->messageChoice = srcPrivKey->messageChoice; switch (destPrivKey->messageChoice) { case crmfThisMessage: case crmfDHMAC: /* I've got a union, so taking the address of one, will also give * me a pointer to the other (eg, message.dhMAC) */ rv = crmf_make_bitstring_copy(poolp, &destPrivKey->message.thisMessage, &srcPrivKey->message.thisMessage); break; case crmfSubsequentMessage: rv = SECITEM_CopyItem(poolp, &destPrivKey->message.subsequentMessage, &srcPrivKey->message.subsequentMessage); break; default: rv = SECFailure; } if (rv != SECSuccess && poolp == NULL) { CRMF_DestroyPOPOPrivKey(destPrivKey); } return rv; }
SECItem * CRMF_POPOSigningKeyGetSignature(CRMFPOPOSigningKey *inSignKey) { SECItem *newSig = NULL; SECStatus rv; PORT_Assert(inSignKey != NULL); if (inSignKey == NULL) { return NULL; } newSig = PORT_ZNew(SECItem); if (newSig == NULL) { goto loser; } rv = crmf_make_bitstring_copy(NULL, newSig, &inSignKey->signature); if (rv != SECSuccess) { goto loser; } return newSig; loser: if (newSig != NULL) { SECITEM_FreeItem(newSig, PR_TRUE); } return NULL; }
SECStatus CRMF_POPOPrivKeyGetDHMAC(CRMFPOPOPrivKey *inKey, SECItem *destMAC) { PORT_Assert(inKey != NULL); if (inKey == NULL || inKey->message.dhMAC.data == NULL) { return SECFailure; } return crmf_make_bitstring_copy(NULL, destMAC, &inKey->message.dhMAC); }
SECStatus CRMF_POPOPrivKeyGetThisMessage(CRMFPOPOPrivKey *inKey, SECItem *destString) { PORT_Assert(inKey != NULL); if (inKey == NULL || inKey->messageChoice != crmfThisMessage) { return SECFailure; } return crmf_make_bitstring_copy(NULL, destString, &inKey->message.thisMessage); }
SECStatus CRMF_CertRequestGetCertTemplateSubjectUID(CRMFCertRequest *inCertReq, SECItem *destSubjectUID) { PORT_Assert(inCertReq != NULL); if (inCertReq == NULL) { return SECFailure; } if (CRMF_DoesRequestHaveField(inCertReq, crmfSubjectUID)) { return crmf_make_bitstring_copy(NULL, destSubjectUID, &inCertReq->certTemplate.subjectUID); } return SECFailure; }
static SECStatus crmf_copy_poposigningkey(PLArenaPool *poolp, CRMFPOPOSigningKey *inPopoSignKey, CRMFPOPOSigningKey *destPopoSignKey) { SECStatus rv; /* We don't support use of the POPOSigningKeyInput, so we'll only * store away the DER encoding. */ if (inPopoSignKey->derInput.data != NULL) { rv = SECITEM_CopyItem(poolp, &destPopoSignKey->derInput, &inPopoSignKey->derInput); } destPopoSignKey->algorithmIdentifier = (poolp == NULL) ? PORT_ZNew(SECAlgorithmID) : PORT_ArenaZNew(poolp, SECAlgorithmID); if (destPopoSignKey->algorithmIdentifier == NULL) { goto loser; } rv = SECOID_CopyAlgorithmID(poolp, destPopoSignKey->algorithmIdentifier, inPopoSignKey->algorithmIdentifier); if (rv != SECSuccess) { goto loser; } rv = crmf_make_bitstring_copy(poolp, &destPopoSignKey->signature, &inPopoSignKey->signature); if (rv != SECSuccess) { goto loser; } return SECSuccess; loser: if (poolp == NULL) { CRMF_DestroyPOPOSigningKey(destPopoSignKey); } return SECFailure; }
static SECItem * crmf_get_encvalue_bitstring(SECItem *srcItem) { SECItem *newItem = NULL; SECStatus rv; if (srcItem->data == NULL) { return NULL; } newItem = PORT_ZNew(SECItem); if (newItem == NULL) { goto loser; } rv = crmf_make_bitstring_copy(NULL, newItem, srcItem); if (rv != SECSuccess) { goto loser; } return newItem; loser: if (newItem != NULL) { SECITEM_FreeItem(newItem, PR_TRUE); } return NULL; }
CRMFEncryptedValue * crmf_create_encrypted_value_wrapped_privkey(SECKEYPrivateKey *inPrivKey, SECKEYPublicKey *inCAKey, CRMFEncryptedValue *destValue) { SECItem wrappedPrivKey, wrappedSymKey; SECItem encodedParam, *dummy; SECStatus rv; CK_MECHANISM_TYPE pubMechType, symKeyType; unsigned char *wrappedSymKeyBits; unsigned char *wrappedPrivKeyBits; SECItem *iv = NULL; SECOidTag tag; PK11SymKey *symKey; PK11SlotInfo *slot; SECAlgorithmID *symmAlg; CRMFEncryptedValue *myEncrValue = NULL; encodedParam.data = NULL; wrappedSymKeyBits = PORT_NewArray(unsigned char, MAX_WRAPPED_KEY_LEN); wrappedPrivKeyBits = PORT_NewArray(unsigned char, MAX_WRAPPED_KEY_LEN); if (wrappedSymKeyBits == NULL || wrappedPrivKeyBits == NULL) { goto loser; } if (destValue == NULL) { myEncrValue = destValue = PORT_ZNew(CRMFEncryptedValue); if (destValue == NULL) { goto loser; } } pubMechType = crmf_get_mechanism_from_public_key(inCAKey); if (pubMechType == CKM_INVALID_MECHANISM) { /* XXX I should probably do something here for non-RSA * keys that are in certs. (ie DSA) * XXX or at least SET AN ERROR CODE. */ goto loser; } slot = inPrivKey->pkcs11Slot; PORT_Assert(slot != NULL); symKeyType = crmf_get_best_privkey_wrap_mechanism(slot); symKey = PK11_KeyGen(slot, symKeyType, NULL, 0, NULL); if (symKey == NULL) { goto loser; } wrappedSymKey.data = wrappedSymKeyBits; wrappedSymKey.len = MAX_WRAPPED_KEY_LEN; rv = PK11_PubWrapSymKey(pubMechType, inCAKey, symKey, &wrappedSymKey); if (rv != SECSuccess) { goto loser; } /* Make the length of the result a Bit String length. */ wrappedSymKey.len <<= 3; wrappedPrivKey.data = wrappedPrivKeyBits; wrappedPrivKey.len = MAX_WRAPPED_KEY_LEN; iv = crmf_get_iv(symKeyType); rv = PK11_WrapPrivKey(slot, symKey, inPrivKey, symKeyType, iv, &wrappedPrivKey, NULL); PK11_FreeSymKey(symKey); if (rv != SECSuccess) { goto loser; } /* Make the length of the result a Bit String length. */ wrappedPrivKey.len <<= 3; rv = crmf_make_bitstring_copy(NULL, &destValue->encValue, &wrappedPrivKey); if (rv != SECSuccess) { goto loser; } rv = crmf_make_bitstring_copy(NULL, &destValue->encSymmKey, &wrappedSymKey); if (rv != SECSuccess) { goto loser; } destValue->symmAlg = symmAlg = PORT_ZNew(SECAlgorithmID); if (symmAlg == NULL) { goto loser; } dummy = SEC_ASN1EncodeItem(NULL, &encodedParam, iv, SEC_ASN1_GET(SEC_OctetStringTemplate)); if (dummy != &encodedParam) { SECITEM_FreeItem(dummy, PR_TRUE); goto loser; } symKeyType = crmf_get_non_pad_mechanism(symKeyType); tag = PK11_MechanismToAlgtag(symKeyType); rv = SECOID_SetAlgorithmID(NULL, symmAlg, tag, &encodedParam); if (rv != SECSuccess) { goto loser; } SECITEM_FreeItem(&encodedParam, PR_FALSE); PORT_Free(wrappedPrivKeyBits); PORT_Free(wrappedSymKeyBits); SECITEM_FreeItem(iv, PR_TRUE); return destValue; loser: if (iv != NULL) { SECITEM_FreeItem(iv, PR_TRUE); } if (myEncrValue != NULL) { crmf_destroy_encrypted_value(myEncrValue, PR_TRUE); } if (wrappedSymKeyBits != NULL) { PORT_Free(wrappedSymKeyBits); } if (wrappedPrivKeyBits != NULL) { PORT_Free(wrappedPrivKeyBits); } if (encodedParam.data != NULL) { SECITEM_FreeItem(&encodedParam, PR_FALSE); } return NULL; }
SECStatus crmf_copy_encryptedvalue(PLArenaPool *poolp, CRMFEncryptedValue *srcValue, CRMFEncryptedValue *destValue) { SECStatus rv; if (srcValue->intendedAlg != NULL) { rv = crmf_copy_encryptedvalue_secalg(poolp, srcValue->intendedAlg, &destValue->intendedAlg); if (rv != SECSuccess) { goto loser; } } if (srcValue->symmAlg != NULL) { rv = crmf_copy_encryptedvalue_secalg(poolp, srcValue->symmAlg, &destValue->symmAlg); if (rv != SECSuccess) { goto loser; } } if (srcValue->encSymmKey.data != NULL) { rv = crmf_make_bitstring_copy(poolp, &destValue->encSymmKey, &srcValue->encSymmKey); if (rv != SECSuccess) { goto loser; } } if (srcValue->keyAlg != NULL) { rv = crmf_copy_encryptedvalue_secalg(poolp, srcValue->keyAlg, &destValue->keyAlg); if (rv != SECSuccess) { goto loser; } } if (srcValue->valueHint.data != NULL) { rv = SECITEM_CopyItem(poolp, &destValue->valueHint, &srcValue->valueHint); if (rv != SECSuccess) { goto loser; } } if (srcValue->encValue.data != NULL) { rv = crmf_make_bitstring_copy(poolp, &destValue->encValue, &srcValue->encValue); if (rv != SECSuccess) { goto loser; } } return SECSuccess; loser: if (poolp == NULL && destValue != NULL) { crmf_destroy_encrypted_value(destValue, PR_FALSE); } return SECFailure; }