case TCG_PTS_GET_AIK:
{
- certificate_t *aik_cert;
- public_key_t *aik_key;
- bool is_naked_key;
+ certificate_t *aik;
- if (!pts->get_aik(pts, &aik_cert, &aik_key, &is_naked_key))
+ aik = pts->get_aik(pts);
+ if (!aik)
{
- DBG1(DBG_IMC, "Obtaining AIK Certificate failed");
+ DBG1(DBG_IMC, "no AIK certificate or public key available");
break;
}
/* Send AIK attribute */
- if(!is_naked_key && aik_cert)
- {
- attr = tcg_pts_attr_aik_create(is_naked_key, chunk_from_thing(aik_cert));
- }
- else if(is_naked_key && aik_key)
- {
- attr = tcg_pts_attr_aik_create(is_naked_key, chunk_from_thing(aik_key));
- }
- else
- {
- DBG1(DBG_IMC, "Neither AIK Certificate nor AIK public was provided");
- break;
- }
+ attr = tcg_pts_attr_aik_create(aik);
attr_list->insert_last(attr_list, attr);
break;
}
case TCG_PTS_AIK:
{
tcg_pts_attr_aik_t *attr_cast;
- chunk_t aik;
- bool is_naked_key;
-
+ certificate_t *aik;
+
attr_cast = (tcg_pts_attr_aik_t*)attr;
aik = attr_cast->get_aik(attr_cast);
- is_naked_key = attr_cast->get_naked_flag(attr_cast);
-
- if(!is_naked_key)
+ if (!aik)
{
- certificate_t *aik_cert;
-
- aik_cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509,
- BUILD_BLOB_PEM, aik,
- BUILD_END);
- pts->set_aik_cert(pts, aik_cert);
- }
- else
- {
- public_key_t *aik_key;
-
- aik_key = lib->creds->create(lib->creds, CRED_PUBLIC_KEY, KEY_ANY,
- BUILD_BLOB_PEM, aik,
- BUILD_END);
- pts->set_aik_key(pts, aik_key);
+ /* TODO generate error attribute */
+ break;
}
-
+ pts->set_aik(pts, aik);
attestation_state->set_handshake_state(attestation_state,
IMV_ATTESTATION_STATE_END);
break;
chunk_t tpm_version_info;
/**
- * Contains a Attestation Identity Certificate
+ * Contains a Attestation Identity Key or Certificate
*/
- certificate_t *aik_cert;
-
- /**
- * Contains a Attestation Identity Public Key
- */
- public_key_t *aik_key;
-
- /**
- * True if AIK is naked public key, not a certificate
- */
- bool is_naked_key;
+ certificate_t *aik;
};
print_tpm_version_info(this);
}
-
/**
- * Obtain an AIK Certificate or public key
- * If the certificate is available in give path, ignore whether key is there
- * If certificate is not available take the public key at given path
+ * Load an AIK certificate or public key,
+ * the certificate having precedence over the public key if both are present
*/
-static bool obtain_aik(private_pts_t *this)
+static void load_aik(private_pts_t *this)
{
- char *certificate_path;
- char *key_path;
+ char *cert_path, *key_path;
- certificate_path = lib->settings->get_str(lib->settings,
- "libimcv.plugins.imc-attestation.aikcert", NULL);
-
+ cert_path = lib->settings->get_str(lib->settings,
+ "libimcv.plugins.imc-attestation.aik_cert", NULL);
key_path = lib->settings->get_str(lib->settings,
- "libimcv.plugins.imc-attestation.aikkey", NULL);
+ "libimcv.plugins.imc-attestation.aik_key", NULL);
- DBG2(DBG_IMC,"AIK Certificate path %s",certificate_path);
- DBG2(DBG_IMC,"AIK Public Key path %s", key_path);
-
- if(certificate_path && (this->aik_cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509,
- BUILD_FROM_FILE, certificate_path,
- BUILD_END)))
- {
- this->is_naked_key = FALSE;
- }
- else if(key_path && (this->aik_key = lib->creds->create(lib->creds, CRED_PUBLIC_KEY, KEY_ANY,
- BUILD_FROM_FILE, key_path,
- BUILD_END)))
+ if (cert_path)
{
- this->is_naked_key = TRUE;
- }
- else
- {
- DBG1(DBG_IMC, "Neither AIK Public Key nor AIK Certificate is available");
- return FALSE;
+ DBG2(DBG_IMC,"AIK certificate path %s", cert_path);
+ this->aik = lib->creds->create(lib->creds, CRED_CERTIFICATE,
+ CERT_X509, BUILD_FROM_FILE,
+ cert_path, BUILD_END);
+ if (this->aik)
+ {
+ return;
+ }
}
-
- DBG3(DBG_IMC, "Succeeded at obtaining AIK Certificate from Privacy CA!");
- return TRUE;
-}
-
-METHOD(pts_t, get_aik, bool,
- private_pts_t *this, certificate_t **aik_cert, public_key_t **aik_key, bool *is_naked_key)
-{
- if (obtain_aik(this) != TRUE )
+ if (key_path)
{
- return FALSE;
+ DBG2(DBG_IMC,"AIK public key path %s", key_path);
+ this->aik = lib->creds->create(lib->creds, CRED_CERTIFICATE,
+ CERT_TRUSTED_PUBKEY, BUILD_FROM_FILE,
+ key_path, BUILD_END);
+ if (this->aik)
+ {
+ return;
+ }
}
-
- *aik_cert = this->aik_cert;
- *aik_key = this->aik_key;
- *is_naked_key = this->is_naked_key;
-
- return TRUE;
+ DBG1(DBG_IMC, "neither AIK certificate nor public key is available");
}
-METHOD(pts_t, set_aik_cert, void,
- private_pts_t *this, certificate_t *aik_cert)
+METHOD(pts_t, get_aik, certificate_t*,
+ private_pts_t *this)
{
- this->aik_cert = aik_cert;
- this->is_naked_key = FALSE;
+ return this->aik;
}
-METHOD(pts_t, set_aik_key, void,
- private_pts_t *this, public_key_t *aik_key)
+METHOD(pts_t, set_aik, void,
+ private_pts_t *this, certificate_t *aik)
{
- this->aik_key = aik_key;
- this->is_naked_key = TRUE;
+ DESTROY_IF(this->aik);
+ this->aik = aik->get_ref(aik);
}
/**
METHOD(pts_t, destroy, void,
private_pts_t *this)
{
+ DESTROY_IF(this->aik);
free(this->platform_info);
free(this->tpm_version_info.ptr);
free(this);
.get_tpm_version_info = _get_tpm_version_info,
.set_tpm_version_info = _set_tpm_version_info,
.get_aik = _get_aik,
- .set_aik_cert = _set_aik_cert,
- .set_aik_key = _set_aik_key,
+ .set_aik = _set_aik,
.do_measurements = _do_measurements,
.destroy = _destroy,
},
{
this->has_tpm = TRUE;
this->proto_caps |= PTS_PROTO_CAPS_T;
+ load_aik(this);
}
}
else
void (*set_tpm_version_info)(pts_t *this, chunk_t info);
/**
- * Get Attestation Identity Key
+ * Get Attestation Identity Certificate or Public Key
*
- * @param aik_cert structure containing a AIK naked public certificate
- * @param aik_key structure containing a AIK naked public key
- * @param is_naked_key TRUE if AIK is naked public key, without certificate
- * @return TRUE if AIK available
+ * @return AIK Certificate or Public Key
*/
- bool (*get_aik)(pts_t *this, certificate_t **aik_cert, public_key_t **aik_key, bool *is_naked_key);
+ certificate_t* (*get_aik)(pts_t *this);
/**
- * Set Attestation Identity Certificate
+ * Set Attestation Identity Certificate or Public Key
*
- * @param aik_cert structure containing a AIK naked public certificate
- * @param is_naked_key TRUE if AIK is naked public key, without certificate
+ * @param aik AIK Certificate or Public Key
*/
- void (*set_aik_cert)(pts_t *this, certificate_t *aik_cert);
+ void (*set_aik)(pts_t *this, certificate_t *aik);
/**
- * Set Attestation Identity Key
- *
- * @param aik_key structure containing a AIK naked public key
- * @param is_naked_key TRUE if AIK is naked public key, without certificate
- */
- void (*set_aik_key)(pts_t *this, public_key_t *aik_key);
-
- /**
* Do PTS File Measurements
*
* @param request_id ID of PTS File Measurement Request
* @return PTS File Measurements of NULL if FAILED
*/
pts_file_meas_t* (*do_measurements)(pts_t *this, u_int16_t request_id,
- char *pathname, bool is_directory);
+ char *pathname, bool is_directory);
/**
* Destroys a pts_t object.
* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
*/
-#define PTS_AIK_SIZE 4
-
+#define PTS_AIK_SIZE 4
+#define PTS_AIK_FLAGS_NONE 0
+#define PTS_AIK_FLAGS_NAKED_KEY (1<<7)
/**
* Private data of an tcg_pts_attr_aik_t object.
*/
bool noskip_flag;
/**
- * Naked Public Key flag
- */
- bool naked_pub_aik;
-
- /**
- * Attestation Identity Key
+ * AIK Certificate or Public Key
*/
- chunk_t aik;
+ certificate_t *aik;
};
METHOD(pa_tnc_attr_t, get_vendor_id, pen_t,
private_tcg_pts_attr_aik_t *this)
{
bio_writer_t *writer;
- u_int8_t flags = 0;
+ u_int8_t flags = PTS_AIK_FLAGS_NONE;
+ chunk_t aik_blob;
- writer = bio_writer_create(PTS_AIK_SIZE);
-
- if (this->naked_pub_aik)
+ if (this->aik->get_type(this->aik) == CERT_TRUSTED_PUBKEY)
{
- flags += 128;
+ flags |= PTS_AIK_FLAGS_NAKED_KEY;
}
- writer->write_uint8 (writer, flags);
- writer->write_data(writer, this->aik);
-
+ if (this->aik->get_encoding(this->aik, CERT_ASN1_DER, &aik_blob))
+ {
+ DBG1(DBG_TNC, "encoding of Attestation Identity Key failed");
+ aik_blob = chunk_empty;
+ }
+ writer = bio_writer_create(PTS_AIK_SIZE);
+ writer->write_uint8(writer, flags);
+ writer->write_data (writer, aik_blob);
this->value = chunk_clone(writer->get_buf(writer));
writer->destroy(writer);
}
{
bio_reader_t *reader;
u_int8_t flags;
+ certificate_type_t type;
+ chunk_t aik_blob;
if (this->value.len < PTS_AIK_SIZE)
{
return FAILED;
}
reader = bio_reader_create(this->value);
-
reader->read_uint8(reader, &flags);
- if ((flags >> 7 ) & 1)
- {
- this->naked_pub_aik = true;
- }
-
- reader->read_data (reader, this->value.len - 1, &this->aik);
- this->aik = chunk_clone(this->aik);
+ reader->read_data (reader, reader->remaining(reader), &aik_blob);
+
+ type = (flags & PTS_AIK_FLAGS_NAKED_KEY) ? CERT_TRUSTED_PUBKEY : CERT_X509;
+
+ this->aik = lib->creds->create(lib->creds, CRED_CERTIFICATE, type,
+ BUILD_BLOB_PEM, aik_blob, BUILD_END);
reader->destroy(reader);
+ if (!this->aik)
+ {
+ DBG1(DBG_TNC, "parsing of Attestation Identity Key failed");
+ *offset = 0;
+ return FAILED;
+ }
return SUCCESS;
}
METHOD(pa_tnc_attr_t, destroy, void,
private_tcg_pts_attr_aik_t *this)
{
+ DESTROY_IF(this->aik);
free(this->value.ptr);
- free(this->aik.ptr);
free(this);
}
-METHOD(tcg_pts_attr_aik_t, get_naked_flag, bool,
- private_tcg_pts_attr_aik_t *this)
-{
- return this->naked_pub_aik;
-}
-
-METHOD(tcg_pts_attr_aik_t, set_naked_flag, void,
- private_tcg_pts_attr_aik_t *this, bool naked_pub_aik)
-{
- this->naked_pub_aik = naked_pub_aik;
-}
-
-METHOD(tcg_pts_attr_aik_t, get_aik, chunk_t,
+METHOD(tcg_pts_attr_aik_t, get_aik, certificate_t*,
private_tcg_pts_attr_aik_t *this)
{
return this->aik;
}
-METHOD(tcg_pts_attr_aik_t, set_aik, void,
- private_tcg_pts_attr_aik_t *this,
- chunk_t aik)
-{
- this->aik = aik;
-}
-
/**
* Described in header.
*/
-pa_tnc_attr_t *tcg_pts_attr_aik_create(bool naked_pub_aik, chunk_t aik)
+pa_tnc_attr_t *tcg_pts_attr_aik_create(certificate_t *aik)
{
private_tcg_pts_attr_aik_t *this;
.process = _process,
.destroy = _destroy,
},
- .get_naked_flag = _get_naked_flag,
- .set_naked_flag = _set_naked_flag,
.get_aik = _get_aik,
- .set_aik = _set_aik,
},
.vendor_id = PEN_TCG,
.type = TCG_PTS_AIK,
- .naked_pub_aik = naked_pub_aik,
- .aik = aik,
+ .aik = aik->get_ref(aik),
);
return &this->public.pa_tnc_attribute;
.process = _process,
.destroy = _destroy,
},
- .get_naked_flag = _get_naked_flag,
- .set_naked_flag = _set_naked_flag,
.get_aik = _get_aik,
- .set_aik = _set_aik,
},
.vendor_id = PEN_TCG,
.type = TCG_PTS_AIK,
#include "tcg_attr.h"
#include "pa_tnc/pa_tnc_attr.h"
+#include <credentials/certificates/certificate.h>
+
/**
* Class implementing the TCG PTS Attestation Identity Key attribute
*
pa_tnc_attr_t pa_tnc_attribute;
/**
- * Get Naked Public Key flag
- *
- * @return Naked Public Key flag
- */
- bool (*get_naked_flag)(tcg_pts_attr_aik_t *this);
-
- /**
- * Set Naked Public Key flag
- *
- * @param naked flag
- */
- void (*set_naked_flag)(tcg_pts_attr_aik_t *this,
- bool naked_pub_aik);
-
- /**
* Get AIK
*
- * @return Attestation Identity Key
+ * @return AIK Certificate or Public Key
*/
- chunk_t (*get_aik)(tcg_pts_attr_aik_t *this);
+ certificate_t* (*get_aik)(tcg_pts_attr_aik_t *this);
- /**
- * Set AIK
- *
- * @param flags set of flags
- */
- void (*set_aik)(tcg_pts_attr_aik_t *this,
- chunk_t aik);
};
/**
* Creates an tcg_pts_attr_aik_t object
*
- * @param naked_pub_aik Sender only has naked public key
* @param aik Attestation Identity Key
*/
-pa_tnc_attr_t* tcg_pts_attr_aik_create(bool naked_pub_aik, chunk_t aik);
+pa_tnc_attr_t* tcg_pts_attr_aik_create(certificate_t *aik);
/**
* Creates an tcg_pts_attr_aik_t object from received data