1 // SPDX-License-Identifier: BSD-2-Clause 2 /* 3 * Copyright 2022 Foundries.io Ltd. 4 * Jorge Ramirez-Ortiz <jorge@foundries.io> 5 */ 6 7 #include <assert.h> 8 #include <drivers/versal_nvm.h> 9 #include <drivers/versal_pmc.h> 10 #include <drivers/versal_puf.h> 11 #include <drivers/versal_sha3_384.h> 12 #include <io.h> 13 #include <kernel/panic.h> 14 #include <kernel/tee_common_otp.h> 15 #include <mm/core_memprot.h> 16 #include <string_ext.h> 17 #include <tee/tee_cryp_utl.h> 18 #include <trace.h> 19 #include <utee_defines.h> 20 21 static struct { 22 uint8_t key[HW_UNIQUE_KEY_LENGTH]; 23 bool ready; 24 } huk; 25 26 #define MODULE_SHIFT 8 27 #define MODULE_ID 5 28 #define API_ID(__x) ((MODULE_ID << MODULE_SHIFT) | (__x)) 29 30 #define VERSAL_AES_KEY_SIZE_256 2 31 #define VERSAL_AES_GCM_ENCRYPT 0 32 33 enum versal_aes_key_src { 34 VERSAL_AES_BBRAM_KEY = 0, 35 VERSAL_AES_BBRAM_RED_KEY, 36 VERSAL_AES_BH_KEY, 37 VERSAL_AES_BH_RED_KEY, 38 VERSAL_AES_EFUSE_KEY, 39 VERSAL_AES_EFUSE_RED_KEY, 40 VERSAL_AES_EFUSE_USER_KEY_0, 41 VERSAL_AES_EFUSE_USER_KEY_1, 42 VERSAL_AES_EFUSE_USER_RED_KEY_0, 43 VERSAL_AES_EFUSE_USER_RED_KEY_1, 44 VERSAL_AES_KUP_KEY, 45 VERSAL_AES_PUF_KEY, 46 VERSAL_AES_USER_KEY_0, 47 VERSAL_AES_USER_KEY_1, 48 VERSAL_AES_USER_KEY_2, 49 VERSAL_AES_USER_KEY_3, 50 VERSAL_AES_USER_KEY_4, 51 VERSAL_AES_USER_KEY_5, 52 VERSAL_AES_USER_KEY_6, 53 VERSAL_AES_USER_KEY_7, 54 VERSAL_AES_EXPANDED_KEYS, 55 }; 56 57 #define VERSAL_AES_MAX_KEY_SOURCES VERSAL_AES_USER_KEY_7 58 59 enum versal_crypto_api { 60 VERSAL_AES_INIT = 9U, 61 VERSAL_AES_OP_INIT, 62 VERSAL_AES_UPDATE_AAD, 63 VERSAL_AES_ENCRYPT_UPDATE, 64 VERSAL_AES_ENCRYPT_FINAL, 65 VERSAL_AES_DECRYPT_UPDATE, 66 VERSAL_AES_DECRYPT_FINAL, 67 VERSAL_AES_KEY_ZERO, 68 VERSAL_AES_WRITE_KEY, 69 VERSAL_AES_LOCK_USER_KEY, 70 VERSAL_AES_KEK_DECRYPT, 71 VERSAL_AES_SET_DPA_CM, 72 }; 73 74 struct versal_aes_input_param { 75 uint64_t input_addr; 76 uint32_t input_len; 77 uint32_t is_last; 78 }; 79 80 struct versal_aes_init { 81 uint64_t iv_addr; 82 uint32_t operation; 83 uint32_t key_src; 84 uint32_t key_len; 85 }; 86 87 /* 88 * The PLM is little endian. When programming the keys in uint32_t the driver 89 * will BE swap the values. 90 * 91 * This way the test key below corresponds to the byte array 0xf8, 0x78, 0xb8, 92 * 0x38, 0xd8, 0x58, 0x98, 0x18, 0xe8, 0x68, .... 93 * 94 * NOTICE: This hardcoded value in DEVEL_KEY could have just been zeroes as done 95 * in the weak implementation found in otp_stubs.c. 96 */ 97 #define DEVEL_KEY { \ 98 0xf878b838, 0xd8589818, 0xe868a828, 0xc8488808, \ 99 0xf070b030, 0xd0509010, 0xe060a020, 0xc0408000, \ 100 } 101 102 #define AAD { \ 103 0x67, 0xe2, 0x1c, 0xf3, 0xcb, 0x29, 0xe0, 0xdc, 0xbc, 0x4d, \ 104 0x8b, 0x1d, 0x0c, 0xc5, 0x33, 0x4b, \ 105 } 106 107 #define NONCE { \ 108 0xd2, 0x45, 0x0e, 0x07, 0xea, 0x5d, 0xe0, 0x42, 0x6c, 0x0f, \ 109 0xa1, 0x33, \ 110 } 111 112 static bool versal_persistent_key(enum versal_aes_key_src src, bool *secure) 113 { 114 struct versal_efuse_puf_sec_ctrl_bits puf_ctrl = { }; 115 struct versal_efuse_sec_ctrl_bits ctrl = { }; 116 struct versal_puf_data puf_data = { }; 117 struct versal_puf_cfg cfg = { 118 .global_var_filter = VERSAL_PUF_GLBL_VAR_FLTR_OPTION, 119 .read_option = VERSAL_PUF_READ_FROM_EFUSE_CACHE, 120 .puf_operation = VERSAL_PUF_REGEN_ON_DEMAND, 121 .shutter_value = VERSAL_PUF_SHUTTER_VALUE, 122 #if defined(PLATFORM_FLAVOR_net) 123 .ro_swap_value = VERSAL_PUF_RO_SWAP_VALUE, 124 #endif 125 126 }; 127 128 switch (src) { 129 case VERSAL_AES_EFUSE_USER_KEY_0: 130 if (versal_efuse_read_sec_ctrl(&ctrl)) 131 panic(); 132 133 *secure = ctrl.user_key0_wr_lk; 134 return true; 135 136 case VERSAL_AES_EFUSE_USER_KEY_1: 137 if (versal_efuse_read_sec_ctrl(&ctrl)) 138 panic(); 139 140 *secure = ctrl.user_key1_wr_lk; 141 return true; 142 143 case VERSAL_AES_PUF_KEY: 144 if (versal_efuse_read_puf_sec_ctrl(&puf_ctrl)) 145 panic(); 146 147 if (versal_puf_regenerate(&puf_data, &cfg)) 148 panic(); 149 150 *secure = puf_ctrl.puf_syn_lk; 151 return true; 152 153 case VERSAL_AES_USER_KEY_0: 154 *secure = false; 155 return false; 156 157 default: 158 EMSG("Trying to use an invalid key for the HUK"); 159 panic(); 160 } 161 162 return false; 163 } 164 165 /* Encrypt using an AES-GCM key selectable with CFG_VERSAL_HUK_KEY */ 166 static TEE_Result aes_gcm_encrypt(uint8_t *src, size_t src_len, 167 uint8_t *dst, size_t dst_len) 168 { 169 struct versal_aes_input_param *input = NULL; 170 struct versal_aes_init *init = NULL; 171 struct versal_mbox_mem input_cmd = { }; 172 struct versal_mbox_mem init_buf = { }; 173 struct versal_mbox_mem p = { }; 174 struct versal_mbox_mem q = { }; 175 uint32_t key_data[8] = DEVEL_KEY; 176 uint8_t nce_data[12] = NONCE; 177 uint8_t aad_data[16] = AAD; 178 size_t nce_len = sizeof(nce_data); 179 size_t key_len = sizeof(key_data); 180 size_t aad_len = sizeof(aad_data); 181 TEE_Result ret = TEE_SUCCESS; 182 struct versal_ipi_cmd cmd = { }; 183 bool secure = false; 184 size_t i = 0; 185 uint32_t key_id = CFG_VERSAL_HUK_KEY; 186 187 if (key_id > VERSAL_AES_MAX_KEY_SOURCES) 188 return TEE_ERROR_BAD_PARAMETERS; 189 190 cmd.data[0] = API_ID(VERSAL_AES_INIT); 191 if (versal_pmc_notify(&cmd, NULL, NULL)) { 192 EMSG("AES_INIT error"); 193 return TEE_ERROR_GENERIC; 194 } 195 196 if (!versal_persistent_key(key_id, &secure)) { 197 for (i = 0; i < ARRAY_SIZE(key_data); i++) 198 key_data[i] = TEE_U32_BSWAP(key_data[i]); 199 200 ret = versal_mbox_alloc(key_len, key_data, &p); 201 if (ret) 202 return ret; 203 204 cmd.data[0] = API_ID(VERSAL_AES_WRITE_KEY); 205 cmd.data[1] = VERSAL_AES_KEY_SIZE_256; 206 cmd.data[2] = key_id; 207 reg_pair_from_64(virt_to_phys(p.buf), 208 &cmd.data[4], &cmd.data[3]); 209 cmd.ibuf[0].mem = p; 210 if (versal_pmc_notify(&cmd, NULL, NULL)) { 211 EMSG("AES_WRITE_KEY error"); 212 ret = TEE_ERROR_GENERIC; 213 } 214 versal_mbox_free(&p); 215 memset(&cmd, 0, sizeof(cmd)); 216 if (ret) 217 return ret; 218 } 219 220 /* Trace indication that it is safe to generate a RPMB key */ 221 IMSG("Using %s HUK", secure ? "Production" : "Development"); 222 223 ret = versal_mbox_alloc(sizeof(*init), NULL, &init_buf); 224 if (ret) 225 return ret; 226 ret = versal_mbox_alloc(nce_len, nce_data, &p); 227 if (ret) { 228 versal_mbox_free(&init_buf); 229 return ret; 230 } 231 232 init = init_buf.buf; 233 init->operation = VERSAL_AES_GCM_ENCRYPT; 234 init->key_len = VERSAL_AES_KEY_SIZE_256; 235 init->iv_addr = virt_to_phys(p.buf); 236 init->key_src = key_id; 237 cmd.data[0] = API_ID(VERSAL_AES_OP_INIT); 238 reg_pair_from_64(virt_to_phys(init), &cmd.data[2], &cmd.data[1]); 239 cmd.ibuf[0].mem = init_buf; 240 cmd.ibuf[1].mem = p; 241 if (versal_pmc_notify(&cmd, NULL, NULL)) { 242 EMSG("AES_OP_INIT error"); 243 ret = TEE_ERROR_GENERIC; 244 } 245 versal_mbox_free(&init_buf); 246 versal_mbox_free(&p); 247 memset(&cmd, 0, sizeof(cmd)); 248 if (ret) 249 return ret; 250 251 ret = versal_mbox_alloc(aad_len, aad_data, &p); 252 if (ret) 253 return ret; 254 255 cmd.data[0] = API_ID(VERSAL_AES_UPDATE_AAD); 256 reg_pair_from_64(virt_to_phys(p.buf), &cmd.data[2], &cmd.data[1]); 257 if (p.len % 16) 258 cmd.data[3] = p.alloc_len; 259 else 260 cmd.data[3] = p.len; 261 cmd.ibuf[0].mem = p; 262 if (versal_pmc_notify(&cmd, NULL, NULL)) { 263 EMSG("AES_UPDATE_AAD error"); 264 ret = TEE_ERROR_GENERIC; 265 } 266 versal_mbox_free(&p); 267 memset(&cmd, 0, sizeof(cmd)); 268 if (ret) 269 return ret; 270 271 ret = versal_mbox_alloc(sizeof(*input), NULL, &input_cmd); 272 if (ret) 273 return ret; 274 275 ret = versal_mbox_alloc(src_len, src, &p); 276 if (ret) { 277 versal_mbox_free(&input_cmd); 278 return ret; 279 } 280 ret = versal_mbox_alloc(dst_len, NULL, &q); 281 if (ret) { 282 versal_mbox_free(&p); 283 versal_mbox_free(&input_cmd); 284 return ret; 285 } 286 287 input = input_cmd.buf; 288 input->input_addr = virt_to_phys(p.buf); 289 input->input_len = p.len; 290 input->is_last = true; 291 cmd.data[0] = API_ID(VERSAL_AES_ENCRYPT_UPDATE); 292 reg_pair_from_64(virt_to_phys(input), &cmd.data[2], &cmd.data[1]); 293 reg_pair_from_64(virt_to_phys(q.buf), &cmd.data[4], &cmd.data[3]); 294 cmd.ibuf[0].mem = input_cmd; 295 cmd.ibuf[1].mem = p; 296 cmd.ibuf[2].mem = q; 297 if (versal_pmc_notify(&cmd, NULL, NULL)) { 298 EMSG("AES_UPDATE_PAYLOAD error"); 299 ret = TEE_ERROR_GENERIC; 300 } 301 memcpy(dst, q.buf, dst_len); 302 versal_mbox_free(&q); 303 versal_mbox_free(&p); 304 versal_mbox_free(&input_cmd); 305 memset(&cmd, 0, sizeof(cmd)); 306 if (ret) 307 return ret; 308 309 ret = versal_mbox_alloc(16, NULL, &p); 310 if (ret) 311 return ret; 312 313 cmd.data[0] = API_ID(VERSAL_AES_ENCRYPT_FINAL); 314 reg_pair_from_64(virt_to_phys(p.buf), &cmd.data[2], &cmd.data[1]); 315 if (versal_pmc_notify(&cmd, NULL, NULL)) { 316 EMSG("AES_ENCRYPT_FINAL error"); 317 ret = TEE_ERROR_GENERIC; 318 } 319 versal_mbox_free(&p); 320 memzero_explicit(&cmd, sizeof(cmd)); 321 322 return ret; 323 } 324 325 TEE_Result tee_otp_get_hw_unique_key(struct tee_hw_unique_key *hwkey) 326 { 327 uint32_t dna[EFUSE_DNA_LEN / sizeof(uint32_t)] = { }; 328 uint8_t enc_data[64] = { }; 329 uint8_t sha[48] = { }; 330 TEE_Result ret = TEE_SUCCESS; 331 332 if (huk.ready) 333 goto out; 334 335 if (versal_efuse_read_dna(dna, sizeof(dna))) 336 return TEE_ERROR_GENERIC; 337 338 if (versal_sha3_384((uint8_t *)dna, sizeof(dna), sha, sizeof(sha))) { 339 ret = TEE_ERROR_GENERIC; 340 goto cleanup; 341 } 342 343 if (aes_gcm_encrypt(sha, sizeof(sha), enc_data, sizeof(enc_data))) { 344 ret = TEE_ERROR_GENERIC; 345 goto cleanup; 346 } 347 348 if (tee_hash_createdigest(TEE_ALG_SHA256, enc_data, sizeof(enc_data), 349 huk.key, sizeof(huk.key))) { 350 ret = TEE_ERROR_GENERIC; 351 goto cleanup; 352 } 353 354 cleanup: 355 memzero_explicit(enc_data, sizeof(enc_data)); 356 memzero_explicit(dna, sizeof(dna)); 357 memzero_explicit(sha, sizeof(sha)); 358 359 if (ret) 360 return ret; 361 362 huk.ready = true; 363 out: 364 memcpy(hwkey->data, huk.key, HW_UNIQUE_KEY_LENGTH); 365 return TEE_SUCCESS; 366 } 367