1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Copyright (c) 2019 Fuzhou Rockchip Electronics Co., Ltd 4 */ 5 6 #include <keymaster.h> 7 #include <common.h> 8 #include <boot_rkimg.h> 9 #include <malloc.h> 10 11 #include <optee_include/OpteeClientApiLib.h> 12 #include <optee_include/tee_client_api.h> 13 #include <optee_include/tee_api_defines.h> 14 15 TEEC_Result read_from_keymaster(uint8_t *filename, 16 uint32_t filename_size, 17 uint8_t *data, 18 uint32_t size) 19 { 20 TEEC_Result TeecResult; 21 TEEC_Context TeecContext; 22 TEEC_Session TeecSession; 23 uint32_t ErrorOrigin; 24 TEEC_UUID tempuuid = { 0x1b484ea5, 25 0x698b, 26 0x4142, 27 { 0x82, 0xb8, 0x3a, 28 0xcf, 0x16, 0xe9, 29 0x9e, 0x2a } }; 30 31 TEEC_UUID *TeecUuid = &tempuuid; 32 TEEC_Operation TeecOperation = {0}; 33 struct blk_desc *dev_desc; 34 35 dev_desc = rockchip_get_bootdev(); 36 if (!dev_desc) { 37 printf("%s: dev_desc is NULL!\n", __func__); 38 return -TEEC_ERROR_GENERIC; 39 } 40 41 debug("read_from_keymaster start\n"); 42 OpteeClientApiLibInitialize(); 43 44 TeecResult = TEEC_InitializeContext(NULL, &TeecContext); 45 46 TeecOperation.paramTypes = TEEC_PARAM_TYPES(TEEC_VALUE_INPUT, 47 TEEC_NONE, 48 TEEC_NONE, 49 TEEC_NONE); 50 51 /*0 nand or emmc "security" partition , 1 rpmb*/ 52 if (dev_desc->if_type == IF_TYPE_MMC && dev_desc->devnum == 0)//emmc 53 TeecOperation.params[0].value.a = 1; 54 else if (dev_desc->if_type == IF_TYPE_SCSI)//ufs 55 TeecOperation.params[0].value.a = 1; 56 else 57 TeecOperation.params[0].value.a = 0; 58 59 #ifdef CONFIG_OPTEE_ALWAYS_USE_SECURITY_PARTITION 60 TeecOperation.params[0].value.a = 0; 61 #endif 62 63 TeecResult = TEEC_OpenSession(&TeecContext, 64 &TeecSession, 65 TeecUuid, 66 TEEC_LOGIN_PUBLIC, 67 NULL, 68 &TeecOperation, 69 &ErrorOrigin); 70 71 TEEC_SharedMemory SharedMem0 = {0}; 72 73 SharedMem0.size = filename_size; 74 SharedMem0.flags = 0; 75 76 TeecResult = TEEC_AllocateSharedMemory(&TeecContext, &SharedMem0); 77 78 memcpy(SharedMem0.buffer, filename, SharedMem0.size); 79 80 TEEC_SharedMemory SharedMem1 = {0}; 81 82 SharedMem1.size = size; 83 SharedMem1.flags = 0; 84 85 TeecResult = TEEC_AllocateSharedMemory(&TeecContext, &SharedMem1); 86 87 TeecOperation.params[0].tmpref.buffer = SharedMem0.buffer; 88 TeecOperation.params[0].tmpref.size = SharedMem0.size; 89 90 TeecOperation.params[1].tmpref.buffer = SharedMem1.buffer; 91 TeecOperation.params[1].tmpref.size = SharedMem1.size; 92 93 TeecOperation.paramTypes = TEEC_PARAM_TYPES(TEEC_MEMREF_TEMP_INPUT, 94 TEEC_MEMREF_TEMP_INOUT, 95 TEEC_NONE, 96 TEEC_NONE); 97 98 TeecResult = TEEC_InvokeCommand(&TeecSession, 99 0, 100 &TeecOperation, 101 &ErrorOrigin); 102 103 if (TeecResult == TEEC_SUCCESS) 104 memcpy(data, SharedMem1.buffer, SharedMem1.size); 105 TEEC_ReleaseSharedMemory(&SharedMem0); 106 TEEC_ReleaseSharedMemory(&SharedMem1); 107 TEEC_CloseSession(&TeecSession); 108 TEEC_FinalizeContext(&TeecContext); 109 debug("read_from_keymaster end\n"); 110 111 return TeecResult; 112 } 113 114 TEEC_Result write_to_keymaster(uint8_t *filename, 115 uint32_t filename_size, 116 uint8_t *data, 117 uint32_t data_size) 118 { 119 TEEC_Result TeecResult; 120 TEEC_Context TeecContext; 121 TEEC_Session TeecSession; 122 uint32_t ErrorOrigin; 123 124 TEEC_UUID tempuuid = { 0x1b484ea5, 125 0x698b, 126 0x4142, 127 { 0x82, 0xb8, 0x3a, 128 0xcf, 0x16, 0xe9, 129 0x9e, 0x2a } }; 130 131 TEEC_UUID *TeecUuid = &tempuuid; 132 TEEC_Operation TeecOperation = {0}; 133 struct blk_desc *dev_desc; 134 135 dev_desc = rockchip_get_bootdev(); 136 if (!dev_desc) { 137 printf("%s: dev_desc is NULL!\n", __func__); 138 return -TEEC_ERROR_GENERIC; 139 } 140 141 debug("write_to_keymaster\n"); 142 OpteeClientApiLibInitialize(); 143 144 TeecResult = TEEC_InitializeContext(NULL, &TeecContext); 145 146 TeecOperation.paramTypes = TEEC_PARAM_TYPES(TEEC_VALUE_INPUT, 147 TEEC_NONE, 148 TEEC_NONE, 149 TEEC_NONE); 150 151 /*0 nand or emmc "security" partition , 1 rpmb*/ 152 if (dev_desc->if_type == IF_TYPE_MMC && dev_desc->devnum == 0)//emmc 153 TeecOperation.params[0].value.a = 1; 154 else if (dev_desc->if_type == IF_TYPE_SCSI)//ufs 155 TeecOperation.params[0].value.a = 1; 156 else 157 TeecOperation.params[0].value.a = 0; 158 159 #ifdef CONFIG_OPTEE_ALWAYS_USE_SECURITY_PARTITION 160 TeecOperation.params[0].value.a = 0; 161 #endif 162 163 TeecResult = TEEC_OpenSession(&TeecContext, 164 &TeecSession, 165 TeecUuid, 166 TEEC_LOGIN_PUBLIC, 167 168 NULL, &TeecOperation, &ErrorOrigin); 169 170 TEEC_SharedMemory SharedMem0 = {0}; 171 172 SharedMem0.size = filename_size; 173 SharedMem0.flags = 0; 174 175 TeecResult = TEEC_AllocateSharedMemory(&TeecContext, &SharedMem0); 176 177 memcpy(SharedMem0.buffer, filename, SharedMem0.size); 178 179 TEEC_SharedMemory SharedMem1 = {0}; 180 181 SharedMem1.size = data_size; 182 SharedMem1.flags = 0; 183 184 TeecResult = TEEC_AllocateSharedMemory(&TeecContext, &SharedMem1); 185 186 memcpy(SharedMem1.buffer, data, SharedMem1.size); 187 188 TeecOperation.params[0].tmpref.buffer = SharedMem0.buffer; 189 TeecOperation.params[0].tmpref.size = SharedMem0.size; 190 191 TeecOperation.params[1].tmpref.buffer = SharedMem1.buffer; 192 TeecOperation.params[1].tmpref.size = SharedMem1.size; 193 194 TeecOperation.paramTypes = TEEC_PARAM_TYPES(TEEC_MEMREF_TEMP_INPUT, 195 TEEC_MEMREF_TEMP_INOUT, 196 TEEC_NONE, 197 TEEC_NONE); 198 199 TeecResult = TEEC_InvokeCommand(&TeecSession, 200 1, 201 &TeecOperation, 202 &ErrorOrigin); 203 204 TEEC_ReleaseSharedMemory(&SharedMem0); 205 TEEC_ReleaseSharedMemory(&SharedMem1); 206 TEEC_CloseSession(&TeecSession); 207 TEEC_FinalizeContext(&TeecContext); 208 debug("write_to_keymaster end\n"); 209 debug("TeecResult %x\n", TeecResult); 210 211 return TeecResult; 212 } 213 214 TEEC_Result trusty_write_oem_unlock(uint8_t unlock) 215 { 216 char *file = "oem.unlock"; 217 TEEC_Result ret; 218 219 ret = write_to_keymaster((uint8_t *)file, 220 strlen(file), 221 (uint8_t *)&unlock, 222 1); 223 return ret; 224 } 225 226 TEEC_Result trusty_read_oem_unlock(uint8_t *unlock) 227 { 228 char *file = "oem.unlock"; 229 TEEC_Result ret; 230 231 ret = read_from_keymaster((uint8_t *)file, 232 strlen(file), 233 unlock, 234 1); 235 236 if (ret == TEE_ERROR_ITEM_NOT_FOUND) { 237 debug("init oem unlock status 0"); 238 ret = trusty_write_oem_unlock(0); 239 } 240 241 return ret; 242 } 243