1 // SPDX-License-Identifier: BSD-2-Clause 2 /* 3 * Copyright (c) 2023, The ChromiumOS Authors 4 */ 5 6 #include <kernel/tee_common_otp.h> 7 #include <libfdt.h> 8 #include <stdint.h> 9 #include <string.h> 10 11 static uint8_t dt_huk[HW_UNIQUE_KEY_LENGTH]; 12 static bool dt_huk_initialized; 13 14 static TEE_Result init_widevine_huk_dt_data(void) 15 { 16 int node = 0; 17 int len = 0; 18 void *fdt = NULL; 19 const void *value = NULL; 20 21 if (dt_huk_initialized) 22 return TEE_SUCCESS; 23 24 fdt = get_secure_dt(); 25 if (!fdt) 26 return TEE_ERROR_NO_DATA; 27 28 node = fdt_path_offset(fdt, "/options/op-tee/widevine"); 29 if (node < 0) 30 return TEE_ERROR_ITEM_NOT_FOUND; 31 32 value = fdt_getprop(fdt, node, "op-tee,hardware-unique-key", &len); 33 if (!value) 34 return TEE_ERROR_ITEM_NOT_FOUND; 35 36 if (len >= HW_UNIQUE_KEY_LENGTH) 37 len = HW_UNIQUE_KEY_LENGTH; 38 else 39 return TEE_ERROR_BAD_FORMAT; 40 41 memcpy(dt_huk, value, len); 42 dt_huk_initialized = true; 43 44 return TEE_SUCCESS; 45 } 46 47 service_init(init_widevine_huk_dt_data); 48 49 TEE_Result tee_otp_get_hw_unique_key(struct tee_hw_unique_key *hwkey) 50 { 51 TEE_Result result = TEE_SUCCESS; 52 53 /* 54 * Ensure we get data from the DT, in case called before service_init() 55 * handler. 56 */ 57 result = init_widevine_huk_dt_data(); 58 if (result != TEE_SUCCESS) 59 return result; 60 61 memcpy(hwkey->data, dt_huk, HW_UNIQUE_KEY_LENGTH); 62 63 return TEE_SUCCESS; 64 } 65