Example #1
0
static int
match_localkeyid(hx509_context context,
		 struct private_key *value,
		 hx509_certs certs)
{
    hx509_cert cert;
    hx509_query q;
    int ret;

    if (value->localKeyId.length == 0) {
	hx509_set_error_string(context, 0, HX509_LOCAL_ATTRIBUTE_MISSING,
			       "No local key attribute on private key");
	return HX509_LOCAL_ATTRIBUTE_MISSING;
    }

    _hx509_query_clear(&q);
    q.match |= HX509_QUERY_MATCH_LOCAL_KEY_ID;

    q.local_key_id = &value->localKeyId;

    ret = hx509_certs_find(context, certs, &q, &cert);
    if (ret == 0) {
	
	if (value->private_key)
	    _hx509_cert_assign_key(cert, value->private_key);
	hx509_cert_free(cert);
    }
    return ret;
}
Example #2
0
static int
set_private_key(hx509_context context,
		SecKeychainItemRef itemRef,
		hx509_cert cert)
{
    struct kc_rsa *kc;
    hx509_private_key key;
    RSA *rsa;
    int ret;

    ret = _hx509_private_key_init(&key, NULL, NULL);
    if (ret)
	return ret;

    kc = calloc(1, sizeof(*kc));
    if (kc == NULL)
	_hx509_abort("out of memory");

    kc->item = itemRef;

    rsa = RSA_new();
    if (rsa == NULL)
	_hx509_abort("out of memory");

    /* Argh, fake modulus since OpenSSL API is on crack */
    {
	SecKeychainAttributeList *attrs = NULL;
	uint32_t size;
	void *data;

	rsa->n = BN_new();
	if (rsa->n == NULL) abort();

	ret = getAttribute(itemRef, kSecKeyKeySizeInBits, &attrs);
	if (ret) abort();

	size = *(uint32_t *)attrs->attr[0].data;
	SecKeychainItemFreeAttributesAndData(attrs, NULL);

	kc->keysize = (size + 7) / 8;

	data = malloc(kc->keysize);
	memset(data, 0xe0, kc->keysize);
	BN_bin2bn(data, kc->keysize, rsa->n);
	free(data);
    }
    rsa->e = NULL;

    RSA_set_method(rsa, &kc_rsa_pkcs1_method);
    ret = RSA_set_app_data(rsa, kc);
    if (ret != 1)
	_hx509_abort("RSA_set_app_data");

    _hx509_private_key_assign_rsa(key, rsa);
    _hx509_cert_assign_key(cert, key);

    return 0;
}
Example #3
0
static int
match_keys(hx509_context context, struct private_key *value, hx509_certs certs)
{
    hx509_cursor cursor;
    hx509_cert c;
    int ret, found = HX509_CERT_NOT_FOUND;

    if (value->private_key == NULL) {
	hx509_set_error_string(context, 0, HX509_PRIVATE_KEY_MISSING,
			       "No private key to compare with");
	return HX509_PRIVATE_KEY_MISSING;
    }

    ret = hx509_certs_start_seq(context, certs, &cursor);
    if (ret)
	return ret;

    c = NULL;
    while (1) {
	ret = hx509_certs_next_cert(context, certs, cursor, &c);
	if (ret)
	    break;
	if (c == NULL)
	    break;
	if (_hx509_cert_private_key(c)) {
	    hx509_cert_free(c);
	    continue;
	}

	ret = _hx509_match_keys(c, value->private_key);
	if (ret) {
	    _hx509_cert_assign_key(c, value->private_key);
	    hx509_cert_free(c);
	    found = 0;
	    break;
	}
	hx509_cert_free(c);
    }

    hx509_certs_end_seq(context, certs, cursor);

    if (found)
	hx509_clear_error_string(context);

    return found;
}