1 /****************************************************************************** 2 * 3 * Copyright 2018 NXP 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 * 17 ******************************************************************************/ 18 #define LOG_TAG "LSClient" 19 #include "LsClient.h" 20 #include <dirent.h> 21 #include <log/log.h> 22 #include <pthread.h> 23 #include <stdlib.h> 24 #include "LsLib.h" 25 26 uint8_t datahex(char c); 27 extern bool ese_debug_enabled; 28 static android::sp<ISecureElementHalCallback> cCallback; 29 void* performLSDownload_thread(void* data); 30 /******************************************************************************* 31 ** 32 ** Function: LSC_Start 33 ** 34 ** Description: Starts the LSC update with encrypted data privided in the 35 updater file 36 ** 37 ** Returns: SUCCESS if ok. 38 ** 39 *******************************************************************************/ 40 LSCSTATUS LSC_Start(const char* name, const char* dest, uint8_t* pdata, 41 uint16_t len, uint8_t* respSW) { 42 static const char fn[] = "LSC_Start"; 43 LSCSTATUS status = LSCSTATUS_FAILED; 44 if (name != NULL) { 45 status = Perform_LSC(name, dest, pdata, len, respSW); 46 } else { 47 ALOGE("%s: LS script file is missing", fn); 48 } 49 ALOGD_IF(ese_debug_enabled, "%s: Exit; status=0x0%X", fn, status); 50 return status; 51 } 52 53 /******************************************************************************* 54 ** 55 ** Function: LSC_doDownload 56 ** 57 ** Description: Start LS download process by creating thread 58 ** 59 ** Returns: SUCCESS of ok 60 ** 61 *******************************************************************************/ 62 LSCSTATUS LSC_doDownload( 63 const android::sp<ISecureElementHalCallback>& clientCallback) { 64 static const char fn[] = "LSC_doDownload"; 65 LSCSTATUS status; 66 pthread_t thread; 67 pthread_attr_t attr; 68 pthread_attr_init(&attr); 69 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 70 cCallback = clientCallback; 71 if (pthread_create(&thread, &attr, &performLSDownload_thread, NULL) < 0) { 72 ALOGE("%s: Thread creation failed", fn); 73 status = LSCSTATUS_FAILED; 74 } else { 75 status = LSCSTATUS_SUCCESS; 76 } 77 pthread_attr_destroy(&attr); 78 return status; 79 } 80 81 /******************************************************************************* 82 ** 83 ** Function: performLSDownload_thread 84 ** 85 ** Description: Perform LS during hal init 86 ** 87 ** Returns: None 88 ** 89 *******************************************************************************/ 90 void* performLSDownload_thread(__attribute__((unused)) void* data) { 91 ALOGD_IF(ese_debug_enabled, "%s enter: ", __func__); 92 93 const char* lsUpdateBackupPath = 94 "/data/vendor/secure_element/loaderservice_updater.txt"; 95 const char* lsUpdateBackupOutPath = 96 "/data/vendor/secure_element/loaderservice_updater_out.txt"; 97 98 /*generated SHA-1 string for secureElementLS 99 This will remain constant as handled in secureElement HAL*/ 100 char sha1[] = "6d583e84f2710e6b0f06beebc1a12a1083591373"; 101 uint8_t hash[20] = {0}; 102 103 for (int i = 0; i < 40; i = i + 2) { 104 hash[i / 2] = 105 (((datahex(sha1[i]) & 0x0F) << 4) | (datahex(sha1[i + 1]) & 0x0F)); 106 } 107 108 uint8_t resSW[4] = {0x4e, 0x02, 0x69, 0x87}; 109 FILE* fIn = fopen(lsUpdateBackupPath, "rb"); 110 if (fIn == NULL) { 111 ALOGE("%s Cannot open LS script file %s\n", __func__, lsUpdateBackupPath); 112 ALOGE("%s Error : %s", __func__, strerror(errno)); 113 cCallback->onStateChange(true); 114 } else { 115 ALOGD_IF(ese_debug_enabled, "%s File opened %s\n", __func__, 116 lsUpdateBackupPath); 117 fseek(fIn, 0, SEEK_END); 118 long fsize = ftell(fIn); 119 rewind(fIn); 120 121 char* lsUpdateBuf = (char*)phNxpEse_memalloc(fsize + 1); 122 fread(lsUpdateBuf, fsize, 1, fIn); 123 124 FILE* fOut = fopen(lsUpdateBackupOutPath, "wb+"); 125 if (fOut == NULL) { 126 ALOGE("%s Failed to open file %s\n", __func__, lsUpdateBackupOutPath); 127 phNxpEse_free(lsUpdateBuf); 128 pthread_exit(NULL); 129 cCallback->onStateChange(true); 130 return NULL; 131 } 132 133 long size = fwrite(lsUpdateBuf, 1, fsize, fOut); 134 if (size != fsize) { 135 ALOGE("%s ERROR - Failed to write %ld bytes to file\n", __func__, fsize); 136 phNxpEse_free(lsUpdateBuf); 137 pthread_exit(NULL); 138 cCallback->onStateChange(true); 139 return NULL; 140 } 141 142 LSCSTATUS status = LSC_Start(lsUpdateBackupPath, lsUpdateBackupOutPath, 143 (uint8_t*)hash, (uint16_t)sizeof(hash), resSW); 144 ALOGD_IF(ese_debug_enabled, "%s LSC_Start completed\n", __func__); 145 if (status == LSCSTATUS_SUCCESS) { 146 if (remove(lsUpdateBackupPath) == 0) { 147 ALOGD_IF(ese_debug_enabled, "%s : %s file deleted successfully\n", 148 __func__, lsUpdateBackupPath); 149 } else { 150 ALOGD_IF(ese_debug_enabled, "%s : %s file deletion failed!!!\n", 151 __func__, lsUpdateBackupPath); 152 } 153 cCallback->onStateChange(true); 154 } else { 155 ESESTATUS status = phNxpEse_deInit(); 156 if (status == ESESTATUS_SUCCESS) { 157 status = phNxpEse_close(); 158 if (status == ESESTATUS_SUCCESS) { 159 ALOGD_IF(ese_debug_enabled, "%s: Ese_close success\n", __func__); 160 } 161 } else { 162 ALOGE("%s: Ese_deInit failed", __func__); 163 } 164 cCallback->onStateChange(false); 165 } 166 phNxpEse_free(lsUpdateBuf); 167 } 168 pthread_exit(NULL); 169 ALOGD_IF(ese_debug_enabled, "%s pthread_exit\n", __func__); 170 return NULL; 171 } 172 173 /******************************************************************************* 174 ** 175 ** Function: datahex 176 ** 177 ** Description: Converts char to uint8_t 178 ** 179 ** Returns: uint8_t variable 180 ** 181 *******************************************************************************/ 182 uint8_t datahex(char c) { 183 uint8_t value = 0; 184 if (c >= '0' && c <= '9') 185 value = (c - '0'); 186 else if (c >= 'A' && c <= 'F') 187 value = (10 + (c - 'A')); 188 else if (c >= 'a' && c <= 'f') 189 value = (10 + (c - 'a')); 190 return value; 191 } 192