From 98d36e5b02f859866da6782a8ad73b0d26d781e8 Mon Sep 17 00:00:00 2001
From: Vivek Gautam <vivek.gautam@arm.com>
Date: Tue, 28 Mar 2023 21:44:56 +0100
Subject: [PATCH] feat(psa): introduce generic library for CCA attestation

Add a generic Arm CCA attestation library driver to interface with the
PSA delegated attestation partition APIs that use RSE to fetch the
platform attestation token and Realm attestation key.

Signed-off-by: Rohit Mathew <rohit.mathew@arm.com>
Signed-off-by: Vivek Gautam <vivek.gautam@arm.com>
Change-Id: I882273e97567cc068f90d2ef089410f3a93c6b00
---
 include/lib/psa/cca_attestation.h | 20 ++++++++++
 lib/psa/cca_attestation.c         | 66 +++++++++++++++++++++++++++++++
 2 files changed, 86 insertions(+)
 create mode 100644 include/lib/psa/cca_attestation.h
 create mode 100644 lib/psa/cca_attestation.c

diff --git a/include/lib/psa/cca_attestation.h b/include/lib/psa/cca_attestation.h
new file mode 100644
index 000000000..4062ddef1
--- /dev/null
+++ b/include/lib/psa/cca_attestation.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CCA_ATTESTATION_H
+#define CCA_ATTESTATION_H
+
+#include <stdint.h>
+#include <psa/crypto_types.h>
+
+psa_status_t
+cca_attestation_get_realm_key(uintptr_t buf, size_t *len, unsigned int type);
+
+psa_status_t
+cca_attestation_get_plat_token(uintptr_t buf, size_t *len,
+			       uintptr_t hash, size_t hash_size);
+
+#endif /* CCA_ATTESTATION_H */
diff --git a/lib/psa/cca_attestation.c b/lib/psa/cca_attestation.c
new file mode 100644
index 000000000..9e9e0c11f
--- /dev/null
+++ b/lib/psa/cca_attestation.c
@@ -0,0 +1,66 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <psa/crypto_sizes.h>
+#include <psa/crypto_types.h>
+#include <psa/crypto_values.h>
+
+#include <cca_attestation.h>
+#include <delegated_attestation.h>
+#include <services/rmmd_svc.h>
+
+psa_status_t
+cca_attestation_get_realm_key(uintptr_t buf, size_t *len, unsigned int type)
+{
+	size_t dak_len;
+	psa_status_t ret = PSA_SUCCESS;
+
+	/*
+	 * Current RMM implementations only support the public key size for
+	 * ECC-P384, i.e. ATTEST_KEY_CURVE_ECC_SECP384R1 attestation key.
+	 *
+	 * This ECC key has following properties:
+	 * ecc_curve:	0x12 (PSA_ECC_FAMILY_SECP_R1)
+	 * key_bits:	384
+	 * hash_alg:	0x02000009 (PSA_ALG_SHA_256)
+	 */
+	assert(type == ATTEST_KEY_CURVE_ECC_SECP384R1);
+
+	ret = rse_delegated_attest_get_delegated_key(PSA_ECC_FAMILY_SECP_R1,
+						     384, (uint8_t *)buf, *len,
+						     &dak_len, PSA_ALG_SHA_256);
+	if (ret != PSA_SUCCESS) {
+		return ret;
+	}
+
+	if (dak_len != PSA_BITS_TO_BYTES(384)) {
+		return PSA_ERROR_INVALID_ARGUMENT;
+	}
+
+	*len = dak_len;
+
+	return ret;
+}
+
+psa_status_t
+cca_attestation_get_plat_token(uintptr_t buf, size_t *len,
+			       uintptr_t hash, size_t hash_size)
+{
+	size_t token_len = 0;
+	psa_status_t ret = PSA_SUCCESS;
+
+	ret = rse_delegated_attest_get_token((const uint8_t *)hash, hash_size,
+					     (uint8_t *)buf, *len, &token_len);
+	if (ret != PSA_SUCCESS) {
+		return ret;
+	}
+
+	*len = token_len;
+
+	return ret;
+}