static int ccrsa_priv_init(ccrsa_priv_ctx_t privkey, size_t p_size, const uint8_t* p, size_t q_size, const uint8_t* q, size_t dp_size, const uint8_t* dp, size_t dq_size, const uint8_t* dq, size_t qinv_size, const uint8_t* qinv) { int result = -1; const cc_size np = cczp_n(ccrsa_ctx_private_zp(privkey)); cc_size nq = cczp_n(ccrsa_ctx_private_zq(privkey)); if (ccn_read_uint(np, CCZP_PRIME(ccrsa_ctx_private_zp(privkey)), p_size, p)) goto errOut; cczp_init(ccrsa_ctx_private_zp(privkey)); if (ccn_read_uint(np, ccrsa_ctx_private_dp(privkey), dp_size, dp)) goto errOut; if (ccn_read_uint(np, ccrsa_ctx_private_qinv(privkey), qinv_size, qinv)) goto errOut; if (ccn_read_uint(nq, CCZP_PRIME(ccrsa_ctx_private_zq(privkey)), q_size, q)) goto errOut; nq = ccn_n(nq, cczp_prime(ccrsa_ctx_private_zq(privkey))); CCZP_N(ccrsa_ctx_private_zq(privkey)) = nq; cczp_init(ccrsa_ctx_private_zq(privkey)); if (ccn_read_uint(nq, ccrsa_ctx_private_dq(privkey), dq_size, dq)) goto errOut; result = 0; errOut: return result; }
CCCryptorStatus CCRSACryptorCreateFromData( CCRSAKeyType keyType, uint8_t *modulus, size_t modulusLength, uint8_t *exponent, size_t exponentLength, uint8_t *p, size_t pLength, uint8_t *q, size_t qLength, CCRSACryptorRef *ref) { CCCryptorStatus retval = kCCSuccess; CCRSACryptor *rsaKey = NULL; size_t n = ccn_nof_size(modulusLength); cc_unit m[n]; CC_DEBUG_LOG(ASL_LEVEL_ERR, "Entering\n"); __Require_Action(ccn_read_uint(n, m, modulusLength, modulus) == 0, errOut, retval = kCCParamError); size_t nbits = ccn_bitlen(n, m); __Require_Action((rsaKey = ccMallocRSACryptor(nbits, keyType)) != NULL, errOut, retval = kCCMemoryFailure); __Require_Action(ccn_read_uint(n, ccrsa_ctx_m(rsaKey->fk), modulusLength, modulus) == 0, errOut, retval = kCCParamError); __Require_Action(ccn_read_uint(n, ccrsa_ctx_e(rsaKey->fk), exponentLength, exponent) == 0, errOut, retval = kCCParamError); cczp_init(ccrsa_ctx_zm(rsaKey->fk)); rsaKey->keySize = ccn_bitlen(n, ccrsa_ctx_m(rsaKey->fk)); switch(keyType) { case ccRSAKeyPublic: rsaKey->keyType = ccRSAKeyPublic; break; case ccRSAKeyPrivate: { ccrsa_priv_ctx_t privk = ccrsa_ctx_private(rsaKey->fk); size_t psize = ccn_nof_size(pLength); size_t qsize = ccn_nof_size(qLength); CCZP_N(ccrsa_ctx_private_zp(privk)) = psize; __Require_Action(ccn_read_uint(psize, CCZP_PRIME(ccrsa_ctx_private_zp(privk)), pLength, p) == 0, errOut, retval = kCCParamError); CCZP_N(ccrsa_ctx_private_zq(privk)) = qsize; __Require_Action(ccn_read_uint(qsize, CCZP_PRIME(ccrsa_ctx_private_zq(privk)), qLength, q) == 0, errOut, retval = kCCParamError); ccrsa_crt_makekey(ccrsa_ctx_zm(rsaKey->fk), ccrsa_ctx_e(rsaKey->fk), ccrsa_ctx_d(rsaKey->fk), ccrsa_ctx_private_zp(privk), ccrsa_ctx_private_dp(privk), ccrsa_ctx_private_qinv(privk), ccrsa_ctx_private_zq(privk), ccrsa_ctx_private_dq(privk)); rsaKey->keyType = ccRSAKeyPrivate; break; } default: retval = kCCParamError; goto errOut; } *ref = rsaKey; return kCCSuccess; errOut: if(rsaKey) ccRSACryptorClear(rsaKey); return retval; }
size_t ccder_encode_rsa_priv_size(const ccrsa_full_ctx_t key) { ccrsa_priv_ctx_t privk = ccrsa_ctx_private(key); cc_size n = ccrsa_ctx_n(key); cc_unit version_0[ccn_nof(1)] = {0x00}; return ccder_sizeof(CCDER_CONSTRUCTED_SEQUENCE, ccder_sizeof_integer(ccn_nof(1), version_0) + ccder_sizeof_integer(n, ccrsa_ctx_m(key)) + ccder_sizeof_integer(n, ccrsa_ctx_e(key)) + ccder_sizeof_integer(n, ccrsa_ctx_d(key)) + ccder_sizeof_integer(cczp_n(ccrsa_ctx_private_zp(privk)), cczp_prime(ccrsa_ctx_private_zp(privk))) + ccder_sizeof_integer(cczp_n(ccrsa_ctx_private_zq(privk)), cczp_prime(ccrsa_ctx_private_zq(privk))) + ccder_sizeof_integer(cczp_n(ccrsa_ctx_private_zp(privk)), ccrsa_ctx_private_dp(privk)) + ccder_sizeof_integer(cczp_n(ccrsa_ctx_private_zq(privk)), ccrsa_ctx_private_dq(privk)) + ccder_sizeof_integer(cczp_n(ccrsa_ctx_private_zp(privk)), ccrsa_ctx_private_qinv(privk)) ); }
static OSStatus ccrsa_full_decode(ccrsa_full_ctx_t fullkey, size_t pkcs1_size, const uint8_t* pkcs1) { OSStatus result = errSecParam; DERItem keyItem = {(DERByte *)pkcs1, pkcs1_size}; DERRSAKeyPair decodedKey; require_noerr_action(DERParseSequence(&keyItem, DERNumRSAKeyPairItemSpecs, DERRSAKeyPairItemSpecs, &decodedKey, sizeof(decodedKey)), errOut, result = errSecDecode); require_noerr(ccrsa_pub_init(fullkey, decodedKey.n.length, decodedKey.n.data, decodedKey.e.length, decodedKey.e.data), errOut); ccn_read_uint(ccrsa_ctx_n(fullkey), ccrsa_ctx_d(fullkey), decodedKey.d.length, decodedKey.d.data); { ccrsa_priv_ctx_t privkey = ccrsa_ctx_private(fullkey); CCZP_N(ccrsa_ctx_private_zp(privkey)) = ccn_nof((ccn_bitsof_n(ccrsa_ctx_n(fullkey)) / 2) + 1); CCZP_N(ccrsa_ctx_private_zq(privkey)) = cczp_n(ccrsa_ctx_private_zp(privkey)); // TODO: Actually remember decodedKey.d. require_noerr(ccrsa_priv_init(privkey, decodedKey.p.length, decodedKey.p.data, decodedKey.q.length, decodedKey.q.data, decodedKey.dp.length, decodedKey.dp.data, decodedKey.dq.length, decodedKey.dq.data, decodedKey.qInv.length, decodedKey.qInv.data), errOut); } result = errSecSuccess; errOut: return result; }
int ccrsa_get_fullkey_components(const ccrsa_full_ctx_t key, uint8_t *modulus, size_t *modulusLength, uint8_t *exponent, size_t *exponentLength, uint8_t *p, size_t *pLength, uint8_t *q, size_t *qLength) { cc_size n = ccrsa_ctx_n(key); if(ccCoreZP2pointerAndData(cczp_n(ccrsa_ctx_private_zp(ccrsa_ctx_private(key))), cczp_prime(ccrsa_ctx_private_zp(ccrsa_ctx_private(key))), p, pLength )) return -1; if(ccCoreZP2pointerAndData(cczp_n(ccrsa_ctx_private_zq(ccrsa_ctx_private(key))), cczp_prime(ccrsa_ctx_private_zq(ccrsa_ctx_private(key))), q, qLength )) return -1; if(ccCoreZP2pointerAndData(n, ccrsa_ctx_m(key), modulus, modulusLength )) return -1; if(ccCoreZP2pointerAndData(n, ccrsa_ctx_d(key), exponent, exponentLength )) return -1; return 0; }
void ccrsa_dump_full_key(ccrsa_full_ctx_t key) { ccn_cprint(ccrsa_ctx_n(key), "uint8_t m[] = ", ccrsa_ctx_m(key)); ccn_cprint(ccrsa_ctx_n(key) + 1, "uint8_t rm[] = ", cczp_recip(ccrsa_ctx_zm(key))); ccn_cprint(ccrsa_ctx_n(key), "uint8_t e[] = ", ccrsa_ctx_e(key)); ccn_cprint(ccrsa_ctx_n(key), "uint8_t d[] = ", ccrsa_ctx_d(key)); printf("cc_size np = %lu;\n", cczp_n(ccrsa_ctx_private_zp(ccrsa_ctx_private(key)))); ccn_cprint(cczp_n(ccrsa_ctx_private_zp(ccrsa_ctx_private(key))), "uint8_t p[] = ", cczp_prime(ccrsa_ctx_private_zp(ccrsa_ctx_private(key)))); ccn_cprint(cczp_n(ccrsa_ctx_private_zp(ccrsa_ctx_private(key))) + 1, "uint8_t rp[] = ", cczp_recip(ccrsa_ctx_private_zp(ccrsa_ctx_private(key)))); printf("cc_size nq = %lu;\n", cczp_n(ccrsa_ctx_private_zq(ccrsa_ctx_private(key)))); ccn_cprint(cczp_n(ccrsa_ctx_private_zq(ccrsa_ctx_private(key))), "uint8_t q[] = ", cczp_prime(ccrsa_ctx_private_zq(ccrsa_ctx_private(key)))); ccn_cprint(cczp_n(ccrsa_ctx_private_zq(ccrsa_ctx_private(key))) + 1, "uint8_t rq[] = ", cczp_recip(ccrsa_ctx_private_zq(ccrsa_ctx_private(key)))); ccn_cprint(cczp_n(ccrsa_ctx_private_zp(ccrsa_ctx_private(key))), "uint8_t dp[] = ", ccrsa_ctx_private_dp(ccrsa_ctx_private(key))); ccn_cprint(cczp_n(ccrsa_ctx_private_zq(ccrsa_ctx_private(key))), "uint8_t dq[] = ", ccrsa_ctx_private_dq(ccrsa_ctx_private(key))); ccn_cprint(cczp_n(ccrsa_ctx_private_zp(ccrsa_ctx_private(key))), "uint8_t qinv[] = ", ccrsa_ctx_private_qinv(ccrsa_ctx_private(key))); printf("--\n"); }
static CFDataRef SecRSAPrivateKeyCreatePKCS1(CFAllocatorRef allocator, ccrsa_full_ctx_t fullkey) { ccrsa_priv_ctx_t privkey = ccrsa_ctx_private(fullkey); const cc_size np = cczp_n(ccrsa_ctx_private_zp(privkey)); const cc_size nq = cczp_n(ccrsa_ctx_private_zq(privkey)); size_t m_size = ccn_write_int_size(ccrsa_ctx_n(fullkey), ccrsa_ctx_m(fullkey)); size_t e_size = ccn_write_int_size(ccrsa_ctx_n(fullkey), ccrsa_ctx_e(fullkey)); size_t d_size = ccn_write_int_size(ccrsa_ctx_n(fullkey), ccrsa_ctx_d(fullkey)); size_t p_size = ccn_write_int_size(np, cczp_prime(ccrsa_ctx_private_zp(privkey))); size_t q_size = ccn_write_int_size(nq, cczp_prime(ccrsa_ctx_private_zq(privkey))); size_t dp_size = ccn_write_int_size(np, ccrsa_ctx_private_dp(privkey)); size_t dq_size = ccn_write_int_size(nq, ccrsa_ctx_private_dq(privkey)); size_t qinv_size = ccn_write_int_size(np, ccrsa_ctx_private_qinv(privkey)); const size_t seq_size = 3 + DERLengthOfItem(ASN1_INTEGER, m_size) + DERLengthOfItem(ASN1_INTEGER, e_size) + DERLengthOfItem(ASN1_INTEGER, d_size) + DERLengthOfItem(ASN1_INTEGER, p_size) + DERLengthOfItem(ASN1_INTEGER, q_size) + DERLengthOfItem(ASN1_INTEGER, dp_size) + DERLengthOfItem(ASN1_INTEGER, dq_size) + DERLengthOfItem(ASN1_INTEGER, qinv_size); const size_t result_size = DERLengthOfItem(ASN1_SEQUENCE, seq_size); CFMutableDataRef pkcs1 = CFDataCreateMutable(allocator, result_size); if (pkcs1 == NULL) return NULL; CFDataSetLength(pkcs1, result_size); uint8_t *bytes = CFDataGetMutableBytePtr(pkcs1); *bytes++ = ASN1_CONSTR_SEQUENCE; DERSize itemLength = 4; DEREncodeLength(seq_size, bytes, &itemLength); bytes += itemLength; *bytes++ = ASN1_INTEGER; *bytes++ = 0x01; *bytes++ = 0x00; ccasn_encode_int(ccrsa_ctx_n(fullkey), ccrsa_ctx_m(fullkey), m_size, &bytes); ccasn_encode_int(ccrsa_ctx_n(fullkey), ccrsa_ctx_e(fullkey), e_size, &bytes); ccasn_encode_int(ccrsa_ctx_n(fullkey), ccrsa_ctx_d(fullkey), d_size, &bytes); ccasn_encode_int(np, cczp_prime(ccrsa_ctx_private_zp(privkey)), p_size, &bytes); ccasn_encode_int(nq, cczp_prime(ccrsa_ctx_private_zq(privkey)), q_size, &bytes); ccasn_encode_int(np, ccrsa_ctx_private_dp(privkey), dp_size, &bytes); ccasn_encode_int(nq, ccrsa_ctx_private_dq(privkey), dq_size, &bytes); ccasn_encode_int(np, ccrsa_ctx_private_qinv(privkey), qinv_size, &bytes); return pkcs1; }