1 // SPDX-License-Identifier: BSD-2-Clause
2 /*
3 * Copyright 2020 Pengutronix, Rouven Czerwinski <entwicklung@pengutronix.de>
4 */
5
6 #include <caam_blob.h>
7 #include <caam_common.h>
8 #include <caam_hal_ctrl.h>
9 #include <caam_jr.h>
10 #include <caam_trace.h>
11 #include <caam_utils_mem.h>
12 #include <kernel/tee_common_otp.h>
13 #include <mm/core_memprot.h>
14 #include <stdint.h>
15 #include <string.h>
16 #include <tee/cache.h>
17
18 #define MKVB_SIZE 32
19
20 static uint8_t stored_key[MKVB_SIZE];
21 static bool mkvb_retrieved;
22
caam_blob_mkvb_init(vaddr_t baseaddr)23 enum caam_status caam_blob_mkvb_init(vaddr_t baseaddr)
24 {
25 struct caam_jobctx jobctx = { };
26 enum caam_status res = CAAM_NO_ERROR;
27 struct caambuf buf = { };
28 uint32_t *desc = NULL;
29
30 assert(!mkvb_retrieved);
31
32 res = caam_calloc_align_buf(&buf, MKVB_SIZE);
33 if (res != CAAM_NO_ERROR)
34 goto out;
35
36 desc = caam_calloc_desc(8);
37 if (!desc) {
38 res = CAAM_OUT_MEMORY;
39 goto out_buf;
40 }
41
42 caam_desc_init(desc);
43 caam_desc_add_word(desc, DESC_HEADER(0));
44 caam_desc_add_word(desc, SEQ_OUT_PTR(32));
45 caam_desc_add_ptr(desc, buf.paddr);
46 caam_desc_add_word(desc, BLOB_MSTR_KEY);
47 BLOB_DUMPDESC(desc);
48
49 cache_operation(TEE_CACHEFLUSH, buf.data, buf.length);
50
51 jobctx.desc = desc;
52 res = caam_jr_enqueue(&jobctx, NULL);
53
54 if (res != CAAM_NO_ERROR) {
55 BLOB_TRACE("JR return code: %#"PRIx32, res);
56 BLOB_TRACE("MKVB failed: Job status %#"PRIx32, jobctx.status);
57 } else {
58 cache_operation(TEE_CACHEINVALIDATE, buf.data, MKVB_SIZE);
59 BLOB_DUMPBUF("MKVB", buf.data, buf.length);
60 memcpy(&stored_key, buf.data, buf.length);
61 mkvb_retrieved = true;
62 }
63
64 out_buf:
65 caam_free_desc(&desc);
66 caam_free_buf(&buf);
67 out:
68 caam_hal_ctrl_inc_priblob(baseaddr);
69
70 return res;
71 }
72
tee_otp_get_hw_unique_key(struct tee_hw_unique_key * hwkey)73 TEE_Result tee_otp_get_hw_unique_key(struct tee_hw_unique_key *hwkey)
74 {
75 COMPILE_TIME_ASSERT(sizeof(hwkey->data) <= sizeof(stored_key));
76
77 if (!mkvb_retrieved)
78 return TEE_ERROR_SECURITY;
79
80 memcpy(&hwkey->data, &stored_key, sizeof(hwkey->data));
81 return TEE_SUCCESS;
82 }
83