summaryrefslogtreecommitdiff
path: root/src/libstrongswan/plugins/x509/x509_pkcs10.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/libstrongswan/plugins/x509/x509_pkcs10.c')
-rw-r--r--src/libstrongswan/plugins/x509/x509_pkcs10.c80
1 files changed, 47 insertions, 33 deletions
diff --git a/src/libstrongswan/plugins/x509/x509_pkcs10.c b/src/libstrongswan/plugins/x509/x509_pkcs10.c
index e39e24bff..587fbd5d6 100644
--- a/src/libstrongswan/plugins/x509/x509_pkcs10.c
+++ b/src/libstrongswan/plugins/x509/x509_pkcs10.c
@@ -72,9 +72,9 @@ struct private_x509_pkcs10_t {
chunk_t challengePassword;
/**
- * Signature algorithm
+ * Signature scheme
*/
- int algorithm;
+ signature_params_t *scheme;
/**
* Signature
@@ -124,10 +124,9 @@ METHOD(certificate_t, has_subject, id_match_t,
METHOD(certificate_t, issued_by, bool,
private_x509_pkcs10_t *this, certificate_t *issuer,
- signature_scheme_t *schemep)
+ signature_params_t **scheme)
{
public_key_t *key;
- signature_scheme_t scheme;
bool valid;
if (&this->public.interface.interface != issuer)
@@ -136,27 +135,22 @@ METHOD(certificate_t, issued_by, bool,
}
if (this->self_signed)
{
- return TRUE;
+ valid = TRUE;
}
-
- /* determine signature scheme */
- scheme = signature_scheme_from_oid(this->algorithm);
- if (scheme == SIGN_UNKNOWN)
+ else
{
- return FALSE;
- }
-
- /* get the public key contained in the certificate request */
- key = this->public_key;
- if (!key)
- {
- return FALSE;
+ /* get the public key contained in the certificate request */
+ key = this->public_key;
+ if (!key)
+ {
+ return FALSE;
+ }
+ valid = key->verify(key, this->scheme->scheme, this->scheme->params,
+ this->certificationRequestInfo, this->signature);
}
- valid = key->verify(key, scheme, this->certificationRequestInfo,
- this->signature);
- if (valid && schemep)
+ if (valid && scheme)
{
- *schemep = scheme;
+ *scheme = signature_params_clone(this->scheme);
}
return valid;
}
@@ -410,7 +404,7 @@ static bool parse_certificate_request(private_x509_pkcs10_t *this)
case PKCS10_SUBJECT_PUBLIC_KEY_INFO:
this->public_key = lib->creds->create(lib->creds, CRED_PUBLIC_KEY,
KEY_ANY, BUILD_BLOB_ASN1_DER, object, BUILD_END);
- if (this->public_key == NULL)
+ if (!this->public_key)
{
goto end;
}
@@ -438,7 +432,12 @@ static bool parse_certificate_request(private_x509_pkcs10_t *this)
}
break;
case PKCS10_ALGORITHM:
- this->algorithm = asn1_parse_algorithmIdentifier(object, level, NULL);
+ INIT(this->scheme);
+ if (!signature_params_parse(object, level, this->scheme))
+ {
+ DBG1(DBG_ASN, " unable to parse signature algorithm");
+ goto end;
+ }
break;
case PKCS10_SIGNATURE:
this->signature = chunk_skip(object, 1);
@@ -474,6 +473,7 @@ METHOD(certificate_t, destroy, void,
{
this->subjectAltNames->destroy_offset(this->subjectAltNames,
offsetof(identification_t, destroy));
+ signature_params_destroy(this->scheme);
DESTROY_IF(this->subject);
DESTROY_IF(this->public_key);
chunk_free(&this->encoding);
@@ -530,25 +530,34 @@ static bool generate(private_x509_pkcs10_t *cert, private_key_t *sign_key,
{
chunk_t key_info, subjectAltNames, attributes;
chunk_t extensionRequest = chunk_empty;
- chunk_t challengePassword = chunk_empty;
- signature_scheme_t scheme;
+ chunk_t challengePassword = chunk_empty, sig_scheme = chunk_empty;
identification_t *subject;
subject = cert->subject;
cert->public_key = sign_key->get_public_key(sign_key);
- /* select signature scheme */
- cert->algorithm = hasher_signature_algorithm_to_oid(digest_alg,
- sign_key->get_type(sign_key));
- if (cert->algorithm == OID_UNKNOWN)
+ /* select signature scheme, if not already specified */
+ if (!cert->scheme)
+ {
+ INIT(cert->scheme,
+ .scheme = signature_scheme_from_oid(
+ hasher_signature_algorithm_to_oid(digest_alg,
+ sign_key->get_type(sign_key))),
+ );
+ }
+ if (cert->scheme->scheme == SIGN_UNKNOWN)
+ {
+ return FALSE;
+ }
+ if (!signature_params_build(cert->scheme, &sig_scheme))
{
return FALSE;
}
- scheme = signature_scheme_from_oid(cert->algorithm);
if (!cert->public_key->get_encoding(cert->public_key,
PUBKEY_SPKI_ASN1_DER, &key_info))
{
+ chunk_free(&sig_scheme);
return FALSE;
}
@@ -584,15 +593,16 @@ static bool generate(private_x509_pkcs10_t *cert, private_key_t *sign_key,
key_info,
attributes);
- if (!sign_key->sign(sign_key, scheme, cert->certificationRequestInfo,
- &cert->signature))
+ if (!sign_key->sign(sign_key, cert->scheme->scheme, cert->scheme->params,
+ cert->certificationRequestInfo, &cert->signature))
{
+ chunk_free(&sig_scheme);
return FALSE;
}
cert->encoding = asn1_wrap(ASN1_SEQUENCE, "cmm",
cert->certificationRequestInfo,
- asn1_algorithmIdentifier(cert->algorithm),
+ sig_scheme,
asn1_bitstring("c", cert->signature));
return TRUE;
}
@@ -674,6 +684,10 @@ x509_pkcs10_t *x509_pkcs10_gen(certificate_type_t type, va_list args)
case BUILD_CHALLENGE_PWD:
cert->challengePassword = chunk_clone(va_arg(args, chunk_t));
continue;
+ case BUILD_SIGNATURE_SCHEME:
+ cert->scheme = va_arg(args, signature_params_t*);
+ cert->scheme = signature_params_clone(cert->scheme);
+ continue;
case BUILD_DIGEST_ALG:
digest_alg = va_arg(args, int);
continue;