tls-peer: Use private key enumeration also in TLS versions < 1.2
Until now, key selection was based on tls_client_certificate_type_t and now uses a simple mapping from these types to tls_signature_scheme_t.
This commit is contained in:
parent
d8e42a3d4e
commit
d41d8b0039
|
@ -1350,42 +1350,36 @@ static status_t send_client_hello(private_tls_peer_t *this,
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find a private key suitable to sign Certificate Verify
|
* Convert certificate types to signature schemes so TLS version <= 1.1 can use
|
||||||
|
* the same private key enumeration as newer TLS versions.
|
||||||
*/
|
*/
|
||||||
static private_key_t *find_private_key(private_tls_peer_t *this)
|
static void convert_cert_types(private_tls_peer_t *this)
|
||||||
{
|
{
|
||||||
private_key_t *key = NULL;
|
|
||||||
bio_reader_t *reader;
|
bio_reader_t *reader;
|
||||||
key_type_t type;
|
bio_writer_t *writer;
|
||||||
uint8_t cert;
|
uint8_t type;
|
||||||
|
|
||||||
if (!this->peer)
|
|
||||||
{
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
reader = bio_reader_create(this->cert_types);
|
reader = bio_reader_create(this->cert_types);
|
||||||
while (reader->remaining(reader) && reader->read_uint8(reader, &cert))
|
writer = bio_writer_create(0);
|
||||||
|
while (reader->remaining(reader) && reader->read_uint8(reader, &type))
|
||||||
{
|
{
|
||||||
switch (cert)
|
/* each certificate type is mapped to one signature scheme, which is not
|
||||||
|
* ideal but serves our needs in legacy TLS versions */
|
||||||
|
switch (type)
|
||||||
{
|
{
|
||||||
case TLS_RSA_SIGN:
|
case TLS_RSA_SIGN:
|
||||||
type = KEY_RSA;
|
writer->write_uint16(writer, TLS_SIG_RSA_PKCS1_SHA256);
|
||||||
break;
|
break;
|
||||||
case TLS_ECDSA_SIGN:
|
case TLS_ECDSA_SIGN:
|
||||||
type = KEY_ECDSA;
|
writer->write_uint16(writer, TLS_SIG_ECDSA_SHA256);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
key = lib->credmgr->get_private(lib->credmgr, type,
|
|
||||||
this->peer, this->peer_auth);
|
|
||||||
if (key)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
reader->destroy(reader);
|
reader->destroy(reader);
|
||||||
return key;
|
this->hashsig = writer->extract_buf(writer);
|
||||||
|
writer->destroy(writer);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -1405,33 +1399,32 @@ static status_t send_certificate(private_tls_peer_t *this,
|
||||||
|
|
||||||
version_min = this->tls->get_version_min(this->tls);
|
version_min = this->tls->get_version_min(this->tls);
|
||||||
version_max = this->tls->get_version_max(this->tls);
|
version_max = this->tls->get_version_max(this->tls);
|
||||||
if (version_max > TLS_1_1)
|
if (!this->hashsig.len)
|
||||||
|
{
|
||||||
|
convert_cert_types(this);
|
||||||
|
}
|
||||||
|
enumerator = tls_create_private_key_enumerator(version_min, version_max,
|
||||||
|
this->hashsig, this->peer);
|
||||||
|
if (!enumerator || !enumerator->enumerate(enumerator, &key, &auth))
|
||||||
{
|
{
|
||||||
enumerator = tls_create_private_key_enumerator(version_min, version_max,
|
|
||||||
this->hashsig, this->peer);
|
|
||||||
if (!enumerator)
|
if (!enumerator)
|
||||||
{
|
{
|
||||||
DBG1(DBG_TLS, "no common signature algorithms found");
|
DBG1(DBG_TLS, "no common signature algorithms found");
|
||||||
return FALSE;
|
|
||||||
}
|
}
|
||||||
if (enumerator->enumerate(enumerator, &key, &auth))
|
else
|
||||||
{
|
{
|
||||||
this->private = key->get_ref(key);
|
DBG1(DBG_TLS, "no usable TLS client certificate found for '%Y'",
|
||||||
this->peer_auth->merge(this->peer_auth, auth, FALSE);
|
this->peer);
|
||||||
}
|
}
|
||||||
enumerator->destroy(enumerator);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
this->private = find_private_key(this);
|
|
||||||
}
|
|
||||||
if (!this->private)
|
|
||||||
{
|
|
||||||
DBG1(DBG_TLS, "no usable TLS client certificate found for '%Y'",
|
|
||||||
this->peer);
|
|
||||||
this->peer->destroy(this->peer);
|
this->peer->destroy(this->peer);
|
||||||
this->peer = NULL;
|
this->peer = NULL;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
this->private = key->get_ref(key);
|
||||||
|
this->peer_auth->merge(this->peer_auth, auth, FALSE);
|
||||||
|
}
|
||||||
|
DESTROY_IF(enumerator);
|
||||||
|
|
||||||
/* generate certificate payload */
|
/* generate certificate payload */
|
||||||
certs = bio_writer_create(256);
|
certs = bio_writer_create(256);
|
||||||
|
|
Loading…
Reference in New Issue