Platform: Get attestation private key from OTP on Musca-B1
Change-Id: I3059bc09b1fd07631e0c0213dc176773cdc4a7e5
Signed-off-by: Xu Yong <yong.xu@arm.com>
diff --git a/platform/ext/common/cc312/cc312.c b/platform/ext/common/cc312/cc312.c
index f1a65e3..29fe268 100644
--- a/platform/ext/common/cc312/cc312.c
+++ b/platform/ext/common/cc312/cc312.c
@@ -17,6 +17,8 @@
#include "arm_cmse.h"
#include "mbedtls_cc_util_key_derivation.h"
#include "tfm_attest_hal.h"
+#include "prod_hw_defs.h"
+#include "cc_otp_defs.h"
#define CC312_NULL_CONTEXT "NO SALT!"
@@ -127,7 +129,79 @@
label, label_size,
context, context_size,
key, key_size);
+}
+/*
+ * Count number of zero bits in 32-bit word.
+ * Copied from:
+ * lib/ext/cryptocell-312-runtime/host/src/ \
+ * cc3x_productionlib/common/prod_util.c: CC_PROD_GetZeroCount(..)
+ */
+static int get_zero_bits_count(uint32_t *buf,
+ uint32_t buf_word_size,
+ uint32_t *zero_count)
+{
+ uint32_t val;
+ uint32_t index = 0;
+
+ *zero_count = 0;
+ for (index = 0; index < buf_word_size; index++) {
+ val = buf[index];
+ val = val - ((val >> 1) & 0x55555555);
+ val = (val & 0x33333333) + ((val >> 2) & 0x33333333);
+ val = ((((val + (val >> 4)) & 0xF0F0F0F) * 0x1010101) >> 24);
+ *zero_count += (32 - val);
+ }
+ /* All 0's and all 1's is forbidden */
+ if ((*zero_count == 0)
+ || (*zero_count == buf_word_size*CC_BITS_IN_32BIT_WORD)) {
+ *zero_count = 0;
+ return -1;
+ }
+
+ return 0;
+}
+
+/*
+ * Get attestation private key from CC312 OTP
+ */
+int crypto_hw_accelerator_get_attestation_private_key(uint8_t *buf,
+ uint32_t *size)
+{
+ uint32_t *key = (uint32_t *)buf;
+ uint32_t otp_val;
+ uint32_t otp_zero_count;
+ uint32_t zero_count;
+ int i;
+ int rc;
+
+ if (key == NULL ||
+ *size < CC_OTP_ATTESTATION_KEY_SIZE_IN_WORDS * sizeof(uint32_t)) {
+ return -1;
+ }
+ *size = CC_OTP_ATTESTATION_KEY_SIZE_IN_WORDS * sizeof(uint32_t);
+
+ /* Get provisioned key from OTP, 8 words */
+ for (i = 0; i < CC_OTP_ATTESTATION_KEY_SIZE_IN_WORDS; i++) {
+ CC_PROD_OTP_READ(otp_val, CC_OTP_ATTESTATION_KEY_OFFSET + i);
+ *key = otp_val;
+ key++;
+ }
+
+ /* Verify the zero number of private key */
+ rc = get_zero_bits_count((uint32_t *)buf,
+ CC_OTP_ATTESTATION_KEY_SIZE_IN_WORDS,
+ &zero_count);
+ if (rc) {
+ return -1;
+ }
+
+ CC_PROD_OTP_READ(otp_zero_count, CC_OTP_ATTESTATION_KEY_ZERO_COUNT_OFFSET);
+ if (otp_zero_count != zero_count) {
+ return -1;
+ }
+
+ return 0;
}
int crypto_hw_accelerator_get_rotpk_hash(uint8_t image_id,