aesm_logic.cpp 35 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995
  1. /*
  2. * Copyright (C) 2011-2017 Intel Corporation. All rights reserved.
  3. *
  4. * Redistribution and use in source and binary forms, with or without
  5. * modification, are permitted provided that the following conditions
  6. * are met:
  7. *
  8. * * Redistributions of source code must retain the above copyright
  9. * notice, this list of conditions and the following disclaimer.
  10. * * Redistributions in binary form must reproduce the above copyright
  11. * notice, this list of conditions and the following disclaimer in
  12. * the documentation and/or other materials provided with the
  13. * distribution.
  14. * * Neither the name of Intel Corporation nor the names of its
  15. * contributors may be used to endorse or promote products derived
  16. * from this software without specific prior written permission.
  17. *
  18. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  19. * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  20. * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  21. * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
  22. * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  23. * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
  24. * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  25. * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  26. * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  27. * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  28. * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  29. *
  30. */
  31. #include "QEClass.h"
  32. #include "LEClass.h"
  33. #include "PSEClass.h"
  34. #include "PVEClass.h"
  35. #include "PCEClass.h"
  36. #include "PSEPRClass.h"
  37. #include "arch.h"
  38. #include "sgx_report.h"
  39. #include "sgx_tseal.h"
  40. #include "epid_pve_type.h"
  41. #include "util.h"
  42. #include <assert.h>
  43. #include <time.h>
  44. #include "oal/oal.h"
  45. #include "oal/aesm_thread.h"
  46. #include "aesm_encode.h"
  47. #include "pairing_blob.h"
  48. #include "aesm_epid_blob.h"
  49. #include "aesm_xegd_blob.h"
  50. #include "aesm_logic.h"
  51. #include "pve_logic.h"
  52. #include "qe_logic.h"
  53. #include "pse_op_logic.h"
  54. #include "platform_info_logic.h"
  55. #include "prov_msg_size.h"
  56. #include "se_sig_rl.h"
  57. #include "se_quote_internal.h"
  58. #include "endpoint_select_info.h"
  59. #include "se_wrapper.h"
  60. #include "PSDAService.h"
  61. #include "ippcp.h"
  62. #include "ippcore.h"
  63. #include <time.h>
  64. #include <string>
  65. #include "ippcp.h"
  66. #include "ippcore.h"
  67. #include "prof_fun.h"
  68. #include "upse/helper.h"
  69. #include "aesm_long_lived_thread.h"
  70. #include "sgx_profile.h"
  71. #include "service_enclave_mrsigner.hh"
  72. #define __STDC_FORMAT_MACROS
  73. #include <inttypes.h>
  74. #define CHECK_SERVICE_STATUS if (!is_service_running()) return AESM_SERVICE_STOPPED;
  75. #define CHECK_SGX_STATUS if (g_sgx_device_status != SGX_ENABLED) return AESM_SGX_DEVICE_NOT_AVAILABLE;
  76. AESMLogicMutex AESMLogic::_qe_pve_mutex;
  77. AESMLogicMutex AESMLogic::_pse_mutex;
  78. AESMLogicMutex AESMLogic::_le_mutex;
  79. bool AESMLogic::_is_qe_psvn_set;
  80. bool AESMLogic::_is_pse_psvn_set;
  81. bool AESMLogic::_is_pce_psvn_set;
  82. psvn_t AESMLogic::_qe_psvn;
  83. psvn_t AESMLogic::_pce_psvn;
  84. psvn_t AESMLogic::_pse_psvn;
  85. uint32_t AESMLogic::active_extended_epid_group_id;
  86. static ae_error_t read_global_extended_epid_group_id(uint32_t *xeg_id)
  87. {
  88. char path_name[MAX_PATH];
  89. ae_error_t ae_ret = aesm_get_pathname(FT_PERSISTENT_STORAGE, EXTENDED_EPID_GROUP_ID_FID, path_name, MAX_PATH);
  90. if(AE_SUCCESS != ae_ret){
  91. return ae_ret;
  92. }
  93. FILE * f = fopen(path_name, "r");
  94. if( f == NULL){
  95. return OAL_CONFIG_FILE_ERROR;
  96. }
  97. ae_ret = OAL_CONFIG_FILE_ERROR;
  98. if(fscanf(f, "%" SCNu32, xeg_id)==1){
  99. ae_ret = AE_SUCCESS;
  100. }
  101. fclose(f);
  102. return ae_ret;
  103. }
  104. static ae_error_t set_global_extended_epid_group_id(uint32_t xeg_id)
  105. {
  106. char path_name[MAX_PATH];
  107. ae_error_t ae_ret = aesm_get_pathname(FT_PERSISTENT_STORAGE, EXTENDED_EPID_GROUP_ID_FID, path_name, MAX_PATH);
  108. if(AE_SUCCESS != ae_ret){
  109. return ae_ret;
  110. }
  111. FILE *f = fopen(path_name, "w");
  112. if(f == NULL){
  113. return OAL_CONFIG_FILE_ERROR;
  114. }
  115. ae_ret = OAL_CONFIG_FILE_ERROR;
  116. if(fprintf(f, "%" PRIu32, xeg_id)>0){
  117. ae_ret = AE_SUCCESS;
  118. }
  119. fclose(f);
  120. return ae_ret;
  121. }
  122. uint32_t AESMLogic::get_active_extended_epid_group_id()
  123. {
  124. return active_extended_epid_group_id;
  125. }
  126. static ae_error_t thread_to_load_qe(aesm_thread_arg_type_t arg)
  127. {
  128. epid_blob_with_cur_psvn_t epid_data;
  129. ae_error_t ae_ret = AE_FAILURE;
  130. UNUSED(arg);
  131. AESM_DBG_TRACE("start to load qe");
  132. memset(&epid_data, 0, sizeof(epid_data));
  133. AESMLogicLock lock(AESMLogic::_qe_pve_mutex);
  134. if((ae_ret = EPIDBlob::instance().read(epid_data)) == AE_SUCCESS)
  135. {
  136. AESM_DBG_TRACE("EPID blob is read successfully, loading QE ...");
  137. ae_ret = CQEClass::instance().load_enclave();
  138. if(AE_SUCCESS != ae_ret)
  139. {
  140. AESM_DBG_WARN("fail to load QE: %d", ae_ret);
  141. }else{
  142. AESM_DBG_TRACE("QE loaded successfully");
  143. bool resealed = false;
  144. se_static_assert(SGX_TRUSTED_EPID_BLOB_SIZE_SDK>=SGX_TRUSTED_EPID_BLOB_SIZE_SIK);
  145. // Just take this chance to reseal EPID blob in case TCB is
  146. // upgraded, return value is ignored and no provisioning is
  147. // triggered.
  148. ae_ret = static_cast<ae_error_t>(CQEClass::instance().verify_blob(
  149. epid_data.trusted_epid_blob,
  150. SGX_TRUSTED_EPID_BLOB_SIZE_SDK,
  151. &resealed));
  152. if(AE_SUCCESS != ae_ret)
  153. {
  154. AESM_DBG_WARN("Failed to verify EPID blob: %d", ae_ret);
  155. EPIDBlob::instance().remove();
  156. }else{
  157. uint32_t epid_xeid;
  158. // Check whether EPID blob XEGDID is aligned with active extended group id if it exists.
  159. if ((EPIDBlob::instance().get_extended_epid_group_id(&epid_xeid) == AE_SUCCESS) && (epid_xeid == AESMLogic::get_active_extended_epid_group_id())) {
  160. AESM_DBG_TRACE("EPID blob Verified");
  161. // XEGDID is aligned
  162. if (true == resealed)
  163. {
  164. AESM_DBG_TRACE("EPID blob is resealed");
  165. if ((ae_ret = EPIDBlob::instance().write(epid_data))
  166. != AE_SUCCESS)
  167. {
  168. AESM_DBG_WARN("Failed to update epid blob: %d", ae_ret);
  169. }
  170. }
  171. }
  172. else { // XEGDID is NOT aligned
  173. AESM_DBG_TRACE("XEGDID mismatch in EPIDBlob, remove it...");
  174. EPIDBlob::instance().remove();
  175. }
  176. }
  177. }
  178. }else{
  179. AESM_DBG_TRACE("Fail to read EPID Blob");
  180. }
  181. AESM_DBG_TRACE("QE Thread finished succ");
  182. return AE_SUCCESS;
  183. }
  184. static ae_error_t thread_to_init_pse(aesm_thread_arg_type_t arg)
  185. {
  186. UNUSED(arg);
  187. AESM_DBG_INFO("start to init_ps");
  188. AESMLogicLock lock(AESMLogic::_pse_mutex);
  189. ae_error_t psError = CPSEClass::instance().init_ps();
  190. UNUSED(psError);// To ignore the error that the symbol not used in release mode
  191. AESM_DBG_INFO("init_ps return ( ae %d)", psError);
  192. return AE_SUCCESS;
  193. }
  194. // Must be called when AESM starts
  195. ae_error_t AESMLogic::service_start()
  196. {
  197. AESM_PROFILE_INIT;
  198. ae_error_t ae_ret = AE_SUCCESS;
  199. AESM_LOG_INIT();
  200. #ifdef SGX_USE_OPT_LIB
  201. ippInit();
  202. #endif
  203. AESM_DBG_INFO("aesm service is starting");
  204. // Try to read active extended epid group id from data file
  205. ae_ret = read_global_extended_epid_group_id(&AESMLogic::active_extended_epid_group_id);
  206. if (AE_SUCCESS != ae_ret){
  207. AESM_DBG_INFO("Fail to read extended epid group id, default extended epid group used");
  208. AESMLogic::active_extended_epid_group_id = DEFAULT_EGID; // Use default extended epid group id 0 if it is not available from data file
  209. }
  210. else{
  211. AESM_DBG_INFO("active extended group id %d used", AESMLogic::active_extended_epid_group_id);
  212. }
  213. if (AE_SUCCESS != (XEGDBlob::verify_xegd_by_xgid(active_extended_epid_group_id)) ||
  214. AE_SUCCESS != (EndpointSelectionInfo::verify_file_by_xgid(active_extended_epid_group_id))){// Try to load XEGD and URL file to make sure it is valid
  215. AESM_LOG_WARN_ADMIN("%s", g_admin_event_string_table[SGX_ADMIN_EVENT_PCD_NOT_AVAILABLE]);
  216. AESM_LOG_WARN("%s: original extended epid group id = %d", g_event_string_table[SGX_EVENT_PCD_NOT_AVAILABLE], AESMLogic::active_extended_epid_group_id);
  217. AESMLogic::active_extended_epid_group_id = DEFAULT_EGID;// If the active extended epid group id read from data file is not valid, switch to default extended epid group id
  218. }
  219. ae_ret = CLEClass::instance().load_enclave();
  220. if(AE_SUCCESS != ae_ret)
  221. {
  222. AESM_DBG_INFO("fail to load LE: %d", ae_ret);
  223. AESM_LOG_FATAL("%s", g_event_string_table[SGX_EVENT_SERVICE_UNAVAILABLE]);
  224. return ae_ret;
  225. }
  226. aesm_thread_t qe_thread=NULL, pse_thread=NULL;
  227. ae_error_t aesm_ret1 = aesm_create_thread(thread_to_load_qe, 0,&qe_thread);
  228. ae_error_t aesm_ret2 = aesm_create_thread(thread_to_init_pse, 0, &pse_thread);
  229. if(AE_SUCCESS != aesm_ret1 ){
  230. AESM_DBG_WARN("Fail to create thread to preload QE:%d",aesm_ret1);
  231. }else{
  232. (void)aesm_free_thread(qe_thread);// Release thread handle to free memory
  233. }
  234. if(AE_SUCCESS != aesm_ret2 ){
  235. AESM_DBG_WARN("Fail to create thread to init PSE:%d",aesm_ret2);
  236. }else{
  237. (void)aesm_free_thread(pse_thread);// Release thread handle to free memory
  238. }
  239. start_white_list_thread();
  240. AESM_DBG_TRACE("aesm service is started");
  241. return AE_SUCCESS;
  242. }
  243. void AESMLogic::service_stop()
  244. {
  245. stop_all_long_lived_threads(0);//waiting for pending threads util timeout
  246. CPVEClass::instance().unload_enclave();
  247. CPCEClass::instance().unload_enclave();
  248. CPSEClass::instance().unload_enclave();
  249. CQEClass::instance().unload_enclave();
  250. CLEClass::instance().unload_enclave();
  251. CPSEPRClass::instance().unload_enclave();
  252. AESM_DBG_INFO("start to stop psda service");
  253. PSDAService::instance().stop_service();
  254. stop_all_long_lived_threads(0);
  255. AESM_DBG_INFO("aesm service down");
  256. AESM_LOG_FINI();
  257. AESM_PROFILE_OUTPUT;
  258. }
  259. bool AESMLogic::is_service_running()
  260. {
  261. return true;
  262. }
  263. ae_error_t AESMLogic::save_unverified_white_list(const uint8_t *white_list_cert, uint32_t white_list_cert_size)
  264. {
  265. wl_cert_chain_t old_cert;
  266. const wl_cert_chain_t *p_new_cert = reinterpret_cast<const wl_cert_chain_t *>(white_list_cert);
  267. uint32_t old_cert_size = sizeof(old_cert);
  268. memset(&old_cert, 0, sizeof(old_cert));
  269. if((aesm_read_data(FT_PERSISTENT_STORAGE, AESM_WHITE_LIST_CERT_TO_BE_VERIFY_FID, reinterpret_cast<uint8_t *>(&old_cert), &old_cert_size) == AE_SUCCESS)
  270. && (old_cert_size == sizeof(old_cert)) && (white_list_cert_size >= sizeof(wl_cert_chain_t)))
  271. {
  272. if(_ntohl(p_new_cert->wl_cert.wl_version) <= _ntohl(old_cert.wl_cert.wl_version))
  273. {
  274. AESM_DBG_WARN("White list version downgraded! current version is %d, new version is %d",
  275. _ntohl(old_cert.wl_cert.wl_version), _ntohl(p_new_cert->wl_cert.wl_version));
  276. return OAL_PARAMETER_ERROR; // OAL_PARAMETER_ERROR used here is to indicate the white list is incorrect
  277. }
  278. }
  279. return aesm_write_data(FT_PERSISTENT_STORAGE, AESM_WHITE_LIST_CERT_TO_BE_VERIFY_FID, white_list_cert, white_list_cert_size);
  280. }
  281. aesm_error_t AESMLogic::white_list_register(
  282. const uint8_t *white_list_cert, uint32_t white_list_cert_size)
  283. {
  284. AESM_DBG_INFO("enter function");
  285. AESM_LOG_INFO_ADMIN("%s", g_admin_event_string_table[SGX_ADMIN_EVENT_WL_UPDATE_START]);
  286. CHECK_SERVICE_STATUS;
  287. AESMLogicLock lock(_le_mutex);
  288. CHECK_SERVICE_STATUS;
  289. ae_error_t ret_le = AE_SUCCESS;
  290. aesm_error_t ret = AESM_UNEXPECTED_ERROR;
  291. if (NULL == white_list_cert||0==white_list_cert_size){
  292. AESM_DBG_TRACE("Invalid parameter");
  293. AESM_LOG_ERROR_ADMIN("%s", g_admin_event_string_table[SGX_ADMIN_EVENT_WL_UPDATE_FAIL]);
  294. return AESM_PARAMETER_ERROR;
  295. }
  296. ae_error_t ae_ret = CLEClass::instance().load_enclave();
  297. if (AE_FAILED(ae_ret))
  298. {
  299. switch (ae_ret)
  300. {
  301. case AE_SERVER_NOT_AVAILABLE:
  302. AESM_DBG_WARN("LE not loaded due to AE_SERVER_NOT_AVAILABLE, possible SGX Env Not Ready");
  303. ret_le = save_unverified_white_list(white_list_cert, white_list_cert_size);
  304. break;
  305. case AESM_AE_OUT_OF_EPC:
  306. AESM_DBG_WARN("LE not loaded due to out of EPC");
  307. ret = AESM_OUT_OF_EPC;
  308. goto exit;
  309. default:
  310. AESM_DBG_ERROR("LE not loaded:(ae%d)", ae_ret);
  311. ret = AESM_UNEXPECTED_ERROR;
  312. goto exit;
  313. }
  314. }
  315. else
  316. {
  317. ret_le = static_cast<ae_error_t>(CLEClass::instance().white_list_register(
  318. white_list_cert, white_list_cert_size));
  319. }
  320. switch (ret_le)
  321. {
  322. case AE_SUCCESS:
  323. ret = AESM_SUCCESS;
  324. break;
  325. case LE_INVALID_PARAMETER:
  326. AESM_DBG_TRACE("Invalid parameter");
  327. ret = AESM_PARAMETER_ERROR;
  328. break;
  329. default:
  330. AESM_DBG_WARN("unexpeted error (ae %d)", ret_le);
  331. ret = AESM_UNEXPECTED_ERROR;
  332. break;
  333. }
  334. exit:
  335. // Always log success or failure to the Admin log before returning
  336. if (AE_FAILED(ae_ret) || AE_FAILED(ret_le)) {
  337. AESM_LOG_ERROR_ADMIN("%s", g_admin_event_string_table[SGX_ADMIN_EVENT_WL_UPDATE_FAIL]);
  338. } else {
  339. const wl_cert_chain_t* wl = reinterpret_cast<const wl_cert_chain_t*>(white_list_cert);
  340. AESM_LOG_INFO_ADMIN("%s for Version: %d", g_admin_event_string_table[SGX_ADMIN_EVENT_WL_UPDATE_SUCCESS],
  341. _ntohl(wl->wl_cert.wl_version));
  342. }
  343. return ret;
  344. }
  345. aesm_error_t AESMLogic::get_launch_token(
  346. const uint8_t * mrenclave, uint32_t mrenclave_size,
  347. const uint8_t *public_key, uint32_t public_key_size,
  348. const uint8_t *se_attributes, uint32_t se_attributes_size,
  349. uint8_t * lictoken, uint32_t lictoken_size)
  350. {
  351. AESM_DBG_INFO("enter function");
  352. CHECK_SERVICE_STATUS;
  353. AESMLogicLock lock(_le_mutex);
  354. CHECK_SERVICE_STATUS;
  355. ae_error_t ret_le = AE_SUCCESS;
  356. if (NULL == mrenclave ||
  357. NULL == public_key ||
  358. NULL == se_attributes ||
  359. NULL == lictoken)
  360. {
  361. // Sizes are checked in CLEClass::get_launch_token()
  362. AESM_DBG_TRACE("Invalid parameter");
  363. return AESM_PARAMETER_ERROR;
  364. }
  365. ae_error_t ae_ret = CLEClass::instance().load_enclave();
  366. if(ae_ret == AE_SERVER_NOT_AVAILABLE)
  367. {
  368. AESM_LOG_ERROR("%s", g_event_string_table[SGX_EVENT_SERVICE_UNAVAILABLE]);
  369. AESM_DBG_FATAL("LE not loaded due to AE_SERVER_NOT_AVAILABLE, possible SGX Env Not Ready");
  370. return AESM_NO_DEVICE_ERROR;
  371. }
  372. else if(ae_ret == AESM_AE_OUT_OF_EPC)
  373. {
  374. AESM_DBG_ERROR("LE not loaded due to out of EPC");
  375. return AESM_OUT_OF_EPC;
  376. }
  377. else if(AE_FAILED(ae_ret))
  378. {
  379. AESM_DBG_ERROR("LE not loaded:%d", ae_ret);
  380. return AESM_SERVICE_UNAVAILABLE;
  381. }
  382. ret_le = static_cast<ae_error_t>(CLEClass::instance().get_launch_token(
  383. const_cast<uint8_t *>(mrenclave), mrenclave_size,
  384. const_cast<uint8_t *>(public_key), public_key_size,
  385. const_cast<uint8_t *>(se_attributes), se_attributes_size,
  386. lictoken, lictoken_size));
  387. switch (ret_le)
  388. {
  389. case AE_SUCCESS:
  390. return AESM_SUCCESS;
  391. case LE_INVALID_PARAMETER:
  392. AESM_DBG_TRACE("Invalid parameter");
  393. return AESM_PARAMETER_ERROR;
  394. case LE_INVALID_ATTRIBUTE:
  395. case LE_INVALID_PRIVILEGE_ERROR:
  396. AESM_DBG_TRACE("Launch token error");
  397. return AESM_GET_LICENSETOKEN_ERROR;
  398. case LE_WHITELIST_UNINITIALIZED_ERROR:
  399. AESM_DBG_TRACE("LE whitelist uninitialized error");
  400. return AESM_UNEXPECTED_ERROR;
  401. default:
  402. AESM_DBG_WARN("unexpeted error (ae %d)", ret_le);
  403. return AESM_UNEXPECTED_ERROR;
  404. }
  405. }
  406. /* This function will be called outside aesm(from urts_internal) */
  407. extern "C" sgx_status_t get_launch_token(const enclave_css_t* signature,
  408. const sgx_attributes_t* attribute,
  409. sgx_launch_token_t* launch_token)
  410. {
  411. AESM_DBG_INFO("enter function");
  412. return AESMLogic::get_launch_token(signature, attribute, launch_token);
  413. }
  414. ae_error_t AESMLogic::get_qe_isv_svn(uint16_t& isv_svn)
  415. {
  416. if(!_is_qe_psvn_set){
  417. ae_error_t ae_err = CQEClass::instance().load_enclave();
  418. if(AE_SUCCESS != ae_err){
  419. AESM_DBG_ERROR("Fail to load QE Enclave:(ae %d)",ae_err);
  420. return ae_err;
  421. }
  422. }
  423. assert(_is_qe_psvn_set);
  424. if(0!=memcpy_s(&isv_svn, sizeof(isv_svn), &_qe_psvn.isv_svn, sizeof(_qe_psvn.isv_svn))){
  425. AESM_DBG_ERROR("memcpy failed");
  426. return AE_FAILURE;
  427. }
  428. return AE_SUCCESS;
  429. }
  430. ae_error_t AESMLogic::get_pce_isv_svn(uint16_t& isv_svn)
  431. {
  432. if(!_is_pce_psvn_set){
  433. ae_error_t ae_err = CPCEClass::instance().load_enclave();
  434. if(AE_SUCCESS != ae_err){
  435. AESM_DBG_ERROR("Fail to load PCE Enclave:(ae %d)",ae_err);
  436. return ae_err;
  437. }
  438. }
  439. assert(_is_pce_psvn_set);
  440. if(0!=memcpy_s(&isv_svn, sizeof(isv_svn), &_pce_psvn.isv_svn, sizeof(_pce_psvn.isv_svn))){
  441. AESM_DBG_ERROR("memcpy failed");
  442. return AE_FAILURE;
  443. }
  444. return AE_SUCCESS;
  445. }
  446. ae_error_t AESMLogic::get_pse_isv_svn(uint16_t& isv_svn)
  447. {
  448. ae_error_t retVal = AE_SUCCESS;
  449. if(!_is_pse_psvn_set){
  450. ae_error_t ae_err = CPSEClass::instance().load_enclave();
  451. if(AE_SUCCESS != ae_err){
  452. AESM_DBG_ERROR("Fail to load PSEOP Enclave:(ae %d)",ae_err);
  453. retVal = ae_err;
  454. }
  455. }
  456. if (AE_SUCCESS == retVal) {
  457. assert(_is_pse_psvn_set);
  458. if(0!=memcpy_s(&isv_svn, sizeof(isv_svn), &_pse_psvn.isv_svn, sizeof(_pse_psvn.isv_svn))){
  459. AESM_DBG_ERROR("memcpy failed");
  460. retVal = AE_FAILURE;
  461. }
  462. }
  463. SGX_DBGPRINT_ONE_STRING_TWO_INTS_CREATE_SESSION(__FUNCTION__" returning ", retVal, isv_svn);
  464. return retVal;
  465. }
  466. ae_error_t AESMLogic::get_qe_cpu_svn(sgx_cpu_svn_t& cpu_svn)
  467. {
  468. if(!_is_qe_psvn_set){
  469. ae_error_t ae_err = CQEClass::instance().load_enclave();
  470. if(AE_SUCCESS != ae_err){
  471. AESM_DBG_ERROR("Fail to load QE Enclave:( ae %d)",ae_err);
  472. return ae_err;
  473. }
  474. }
  475. assert(_is_qe_psvn_set);
  476. if(0!=memcpy_s(&cpu_svn, sizeof(sgx_cpu_svn_t), &_qe_psvn.cpu_svn, sizeof(_qe_psvn.cpu_svn))){
  477. AESM_DBG_ERROR("memcpy failed");
  478. return AE_FAILURE;
  479. }
  480. return AE_SUCCESS;
  481. }
  482. ae_error_t AESMLogic::set_psvn(uint16_t prod_id, uint16_t isv_svn, sgx_cpu_svn_t cpu_svn, uint32_t mrsigner_index)
  483. {
  484. if(prod_id == QE_PROD_ID){
  485. if(mrsigner_index == AE_MR_SIGNER){
  486. if(_is_qe_psvn_set){
  487. if(0!=memcmp(&_qe_psvn.isv_svn, &isv_svn, sizeof(isv_svn))||
  488. 0!=memcmp(&_qe_psvn.cpu_svn, &cpu_svn, sizeof(sgx_cpu_svn_t))){
  489. AESM_DBG_ERROR("PSVN unmatched for QE/PVE");
  490. return AE_PSVN_UNMATCHED_ERROR;
  491. }
  492. }else{
  493. if(0!=memcpy_s(&_qe_psvn.isv_svn, sizeof(_qe_psvn.isv_svn), &isv_svn, sizeof(isv_svn))||
  494. 0!=memcpy_s(&_qe_psvn.cpu_svn, sizeof(_qe_psvn.cpu_svn), &cpu_svn, sizeof(sgx_cpu_svn_t))){
  495. AESM_DBG_ERROR("memcpy failed");
  496. return AE_FAILURE;
  497. }
  498. AESM_DBG_TRACE("get QE or PvE isv_svn=%d",(int)isv_svn);
  499. _is_qe_psvn_set = true;
  500. return AE_SUCCESS;
  501. }
  502. }else if(mrsigner_index==PCE_MR_SIGNER){
  503. if(_is_pce_psvn_set){
  504. if(0!=memcmp(&_pce_psvn.isv_svn, &isv_svn, sizeof(isv_svn))||
  505. 0!=memcmp(&_pce_psvn.cpu_svn, &cpu_svn, sizeof(sgx_cpu_svn_t))){
  506. AESM_DBG_ERROR("PSVN unmatched for PCE");
  507. return AE_PSVN_UNMATCHED_ERROR;
  508. }
  509. }else{
  510. if(0!=memcpy_s(&_pce_psvn.isv_svn, sizeof(_pce_psvn.isv_svn), &isv_svn, sizeof(isv_svn))||
  511. 0!=memcpy_s(&_pce_psvn.cpu_svn, sizeof(_pce_psvn.cpu_svn), &cpu_svn, sizeof(sgx_cpu_svn_t))){
  512. AESM_DBG_ERROR("memcpy failed");
  513. return AE_FAILURE;
  514. }
  515. AESM_DBG_TRACE("get PCE isv_svn=%d", (int)isv_svn);
  516. _is_pce_psvn_set = true;
  517. return AE_SUCCESS;
  518. }
  519. }
  520. }else if(prod_id == PSE_PROD_ID){
  521. if(mrsigner_index == AE_MR_SIGNER){
  522. if(_is_pse_psvn_set){
  523. if(0!=memcmp(&_pse_psvn.isv_svn, &isv_svn, sizeof(isv_svn))||
  524. 0!=memcmp(&_pse_psvn.cpu_svn, &cpu_svn, sizeof(sgx_cpu_svn_t))){
  525. AESM_DBG_ERROR("PSVN unmatched for PSE");
  526. return AE_PSVN_UNMATCHED_ERROR;
  527. }
  528. }else{
  529. if(0!=memcpy_s(&_pse_psvn.isv_svn, sizeof(_pse_psvn.isv_svn), &isv_svn, sizeof(isv_svn))||
  530. 0!=memcpy_s(&_pse_psvn.cpu_svn, sizeof(_pse_psvn.cpu_svn), &cpu_svn, sizeof(sgx_cpu_svn_t))){
  531. AESM_DBG_ERROR("memcpy failed");
  532. return AE_FAILURE;
  533. }
  534. AESM_DBG_TRACE("get PSE isv_svn=%d", (int)isv_svn);
  535. _is_pse_psvn_set = true;
  536. return AE_SUCCESS;
  537. }
  538. }
  539. }
  540. return AE_SUCCESS;
  541. }
  542. sgx_status_t AESMLogic::get_launch_token(const enclave_css_t* signature,
  543. const sgx_attributes_t* attribute,
  544. sgx_launch_token_t* launch_token)
  545. {
  546. AESM_DBG_INFO("enter function");
  547. AESMLogicLock lock(_le_mutex);
  548. ae_error_t ret_le = AE_SUCCESS;
  549. uint32_t mrsigner_index = UINT32_MAX;
  550. // load LE to get launch token
  551. if((ret_le=CLEClass::instance().load_enclave()) != AE_SUCCESS)
  552. {
  553. if(ret_le == AESM_AE_NO_DEVICE)
  554. {
  555. AESM_DBG_FATAL("LE not loaded due to no SGX device available, possible SGX Env Not Ready");
  556. return SGX_ERROR_NO_DEVICE;
  557. }
  558. else if(ret_le == AESM_AE_OUT_OF_EPC)
  559. {
  560. AESM_DBG_FATAL("LE not loaded due to out of EPC");
  561. return SGX_ERROR_OUT_OF_EPC;
  562. }
  563. else
  564. {
  565. AESM_DBG_FATAL("fail to load LE:%d",ret_le);
  566. return SGX_ERROR_SERVICE_UNAVAILABLE;
  567. }
  568. }
  569. ret_le = static_cast<ae_error_t>(CLEClass::instance().get_launch_token(
  570. const_cast<uint8_t*>(reinterpret_cast<const uint8_t *>(&signature->body.enclave_hash)),
  571. sizeof(sgx_measurement_t),
  572. const_cast<uint8_t*>(reinterpret_cast<const uint8_t *>(&signature->key.modulus)),
  573. sizeof(signature->key.modulus),
  574. const_cast<uint8_t*>(reinterpret_cast<const uint8_t *>(attribute)),
  575. sizeof(sgx_attributes_t),
  576. reinterpret_cast<uint8_t*>(launch_token),
  577. sizeof(token_t),
  578. &mrsigner_index));
  579. switch (ret_le)
  580. {
  581. case AE_SUCCESS:
  582. break;
  583. case LE_INVALID_PARAMETER:
  584. AESM_DBG_TRACE("Invalid parameter");
  585. return SGX_ERROR_INVALID_PARAMETER;
  586. case LE_INVALID_ATTRIBUTE:
  587. case LE_INVALID_PRIVILEGE_ERROR:
  588. AESM_DBG_TRACE("Launch token error");
  589. return SGX_ERROR_SERVICE_INVALID_PRIVILEGE;
  590. case LE_WHITELIST_UNINITIALIZED_ERROR:
  591. AESM_DBG_TRACE("LE whitelist uninitialized error");
  592. return SGX_ERROR_UNEXPECTED;
  593. default:
  594. AESM_DBG_WARN("unexpected error (ae%d)", ret_le);
  595. return SGX_ERROR_UNEXPECTED;
  596. }
  597. token_t *lt = reinterpret_cast<token_t *>(launch_token);
  598. ret_le = set_psvn(signature->body.isv_prod_id, signature->body.isv_svn, lt->cpu_svn_le, mrsigner_index);
  599. if(AE_PSVN_UNMATCHED_ERROR == ret_le)
  600. {
  601. //QE or PSE has been changed, but AESM doesn't restart. Will not provide service.
  602. return SGX_ERROR_SERVICE_UNAVAILABLE;
  603. }else if(AE_SUCCESS != ret_le) {
  604. AESM_DBG_ERROR("fail to save psvn:(ae%d)", ret_le);
  605. return SGX_ERROR_UNEXPECTED;
  606. }
  607. return SGX_SUCCESS;
  608. }
  609. #define CHECK_LONG_TERM_PAIRING_STATUS \
  610. if(!query_pse_thread_status()){\
  611. return AESM_BUSY; \
  612. }
  613. aesm_error_t AESMLogic::create_session(
  614. uint32_t* session_id,
  615. uint8_t* se_dh_msg1, uint32_t se_dh_msg1_size)
  616. {
  617. AESM_DBG_INFO("AESMLogic::create_session");
  618. CHECK_SERVICE_STATUS;
  619. AESMLogicLock lock(_pse_mutex);
  620. CHECK_SERVICE_STATUS;
  621. CHECK_LONG_TERM_PAIRING_STATUS;
  622. ae_error_t psStatus;
  623. // If PSDA not loaded or CSE not provisioned
  624. if (CPSEClass::instance().get_status() == PSE_STATUS_INIT ||
  625. CPSEClass::instance().get_status() == PSE_STATUS_UNAVAILABLE )
  626. {
  627. AESM_DBG_ERROR("unexpected status PSE_STATUS_INIT : PSDA not loaded or CSE not provisioned.");
  628. return AESM_PSDA_UNAVAILABLE;
  629. }
  630. else
  631. psStatus = PlatformInfoLogic::create_session_pre_internal();
  632. if (OAL_THREAD_TIMEOUT_ERROR == psStatus){
  633. AESM_DBG_INFO("AESM is busy in intializing for pse");
  634. return AESM_BUSY;
  635. }
  636. if (PVE_PROV_ATTEST_KEY_NOT_FOUND == psStatus) {
  637. AESM_DBG_INFO("Key not found reported by Provisioning backend");
  638. return AESM_UNRECOGNIZED_PLATFORM;
  639. }
  640. if(OAL_PROXY_SETTING_ASSIST == psStatus){
  641. AESM_DBG_INFO("Proxy assist required in initializing for pse");
  642. return AESM_PROXY_SETTING_ASSIST;
  643. }
  644. if(PSW_UPDATE_REQUIRED == psStatus){
  645. AESM_DBG_INFO("PSW software update required");
  646. return AESM_UPDATE_AVAILABLE;
  647. }
  648. if(AESM_AE_OUT_OF_EPC == psStatus)
  649. return AESM_OUT_OF_EPC;
  650. if (AE_SUCCESS != psStatus) {
  651. AESM_DBG_ERROR("psStatus = 0x%X in create_session", psStatus);
  652. }
  653. return PSEOPAESMLogic::create_session(session_id, se_dh_msg1, se_dh_msg1_size);
  654. }
  655. aesm_error_t AESMLogic::exchange_report(
  656. uint32_t session_id,
  657. const uint8_t* se_dh_msg2, uint32_t se_dh_msg2_size,
  658. uint8_t* se_dh_msg3, uint32_t se_dh_msg3_size)
  659. {
  660. AESM_DBG_INFO("AESMLogic::exchange_report");
  661. CHECK_SERVICE_STATUS;
  662. AESMLogicLock lock(_pse_mutex);
  663. CHECK_SERVICE_STATUS;
  664. CHECK_LONG_TERM_PAIRING_STATUS;
  665. return PSEOPAESMLogic::exchange_report(session_id,
  666. se_dh_msg2,
  667. se_dh_msg2_size,
  668. se_dh_msg3,
  669. se_dh_msg3_size);
  670. }
  671. aesm_error_t AESMLogic::close_session(
  672. uint32_t session_id)
  673. {
  674. AESM_DBG_INFO("AESMLogic::close_session");
  675. CHECK_SERVICE_STATUS;
  676. AESMLogicLock lock(_pse_mutex);
  677. CHECK_SERVICE_STATUS;
  678. return PSEOPAESMLogic::close_session(session_id);
  679. }
  680. aesm_error_t AESMLogic::invoke_service(
  681. const uint8_t* pse_message_req, uint32_t pse_message_req_size,
  682. uint8_t* pse_message_resp, uint32_t pse_message_resp_size)
  683. {
  684. AESM_DBG_INFO("AESMLogic::invoke_service");
  685. CHECK_SERVICE_STATUS;
  686. AESMLogicLock lock(_pse_mutex);
  687. CHECK_SERVICE_STATUS;
  688. CHECK_LONG_TERM_PAIRING_STATUS;
  689. return PSEOPAESMLogic::invoke_service(pse_message_req,
  690. pse_message_req_size,
  691. pse_message_resp,
  692. pse_message_resp_size);
  693. }
  694. aesm_error_t AESMLogic::get_ps_cap(
  695. uint64_t* ps_cap)
  696. {
  697. AESM_DBG_INFO("AESMLogic::get_ps_cap");
  698. CHECK_SERVICE_STATUS;
  699. AESMLogicLock lock(_pse_mutex);
  700. CHECK_SERVICE_STATUS;
  701. return PSEOPAESMLogic::get_ps_cap(ps_cap);
  702. }
  703. #define CHECK_EPID_PROVISIONG_STATUS \
  704. if(!query_pve_thread_status()){\
  705. return AESM_BUSY;\
  706. }
  707. aesm_error_t AESMLogic::init_quote(
  708. uint8_t *target_info, uint32_t target_info_size,
  709. uint8_t *gid, uint32_t gid_size)
  710. {
  711. ae_error_t ret = AE_SUCCESS;
  712. uint16_t qe_isv_svn = 0xFFFF;
  713. uint16_t pce_isv_svn = 0xFFFF;
  714. sgx_cpu_svn_t qe_cpu_svn;
  715. memset(&qe_cpu_svn, 0, sizeof(qe_cpu_svn));
  716. AESM_DBG_INFO("init_quote");
  717. if(sizeof(sgx_target_info_t) != target_info_size ||
  718. sizeof(sgx_epid_group_id_t) != gid_size)
  719. {
  720. return AESM_PARAMETER_ERROR;
  721. }
  722. AESMLogicLock lock(_qe_pve_mutex);
  723. CHECK_EPID_PROVISIONG_STATUS;
  724. ret = get_pce_isv_svn(pce_isv_svn);
  725. if(AE_SUCCESS != ret)
  726. {
  727. if(AESM_AE_OUT_OF_EPC == ret)
  728. return AESM_OUT_OF_EPC;
  729. else if(AESM_AE_NO_DEVICE == ret)
  730. return AESM_NO_DEVICE_ERROR;
  731. else if(AE_SERVER_NOT_AVAILABLE == ret)
  732. return AESM_SERVICE_UNAVAILABLE;
  733. return AESM_UNEXPECTED_ERROR;
  734. }
  735. ret = get_qe_cpu_svn(qe_cpu_svn);
  736. if(AE_SUCCESS != ret)
  737. {
  738. if(AESM_AE_OUT_OF_EPC == ret)
  739. return AESM_OUT_OF_EPC;
  740. else if(AESM_AE_NO_DEVICE == ret)
  741. return AESM_NO_DEVICE_ERROR;
  742. else if(AE_SERVER_NOT_AVAILABLE == ret)
  743. return AESM_SERVICE_UNAVAILABLE;
  744. return AESM_UNEXPECTED_ERROR;
  745. }
  746. ret = get_qe_isv_svn(qe_isv_svn);
  747. if(AE_SUCCESS != ret)
  748. {
  749. if(AESM_AE_OUT_OF_EPC == ret)
  750. return AESM_OUT_OF_EPC;
  751. else if(AESM_AE_NO_DEVICE == ret)
  752. return AESM_NO_DEVICE_ERROR;
  753. else if(AE_SERVER_NOT_AVAILABLE == ret)
  754. return AESM_SERVICE_UNAVAILABLE;
  755. return AESM_UNEXPECTED_ERROR;
  756. }
  757. return QEAESMLogic::init_quote(
  758. reinterpret_cast<sgx_target_info_t *>(target_info),
  759. gid, gid_size, pce_isv_svn, qe_isv_svn, qe_cpu_svn);
  760. }
  761. aesm_error_t AESMLogic::get_quote(const uint8_t *report, uint32_t report_size,
  762. uint32_t quote_type,
  763. const uint8_t *spid, uint32_t spid_size,
  764. const uint8_t *nonce, uint32_t nonce_size,
  765. const uint8_t *sigrl, uint32_t sigrl_size,
  766. uint8_t *qe_report, uint32_t qe_report_size,
  767. uint8_t *quote, uint32_t buf_size)
  768. {
  769. ae_error_t ret = AE_SUCCESS;
  770. uint16_t pce_isv_svn = 0xFFFF;
  771. AESM_DBG_INFO("get_quote");
  772. if(sizeof(sgx_report_t) != report_size ||
  773. sizeof(sgx_spid_t) != spid_size)
  774. {
  775. return AESM_PARAMETER_ERROR;
  776. }
  777. if((nonce && sizeof(sgx_quote_nonce_t) != nonce_size)
  778. || (qe_report && sizeof(sgx_report_t) != qe_report_size))
  779. {
  780. return AESM_PARAMETER_ERROR;
  781. }
  782. AESMLogicLock lock(_qe_pve_mutex);
  783. CHECK_EPID_PROVISIONG_STATUS;
  784. ret = get_pce_isv_svn(pce_isv_svn);
  785. if(AE_SUCCESS != ret)
  786. {
  787. if(AESM_AE_OUT_OF_EPC == ret)
  788. return AESM_OUT_OF_EPC;
  789. else if(AESM_AE_NO_DEVICE == ret)
  790. return AESM_NO_DEVICE_ERROR;
  791. else if(AE_SERVER_NOT_AVAILABLE == ret)
  792. return AESM_SERVICE_UNAVAILABLE;
  793. return AESM_UNEXPECTED_ERROR;
  794. }
  795. return QEAESMLogic::get_quote(report, quote_type, spid, nonce, sigrl,
  796. sigrl_size, qe_report, quote, buf_size, pce_isv_svn);
  797. }
  798. uint32_t AESMLogic::endpoint_selection(endpoint_selection_infos_t& es_info)
  799. {
  800. AESMLogicLock lock(_qe_pve_mutex);
  801. SGX_DBGPRINT_ONE_STRING_TWO_INTS_ENDPOINT_SELECTION(__FUNCTION__" (line, 0)", __LINE__, 0);
  802. return EndpointSelectionInfo::instance().start_protocol(es_info);
  803. }
  804. uint32_t AESMLogic::is_gid_matching_result_in_epid_blob(const GroupId& gid)
  805. {
  806. AESMLogicLock lock(_qe_pve_mutex);
  807. EPIDBlob& epid_blob = EPIDBlob::instance();
  808. uint32_t le_gid;
  809. if(epid_blob.get_sgx_gid(&le_gid)!=AE_SUCCESS){//get littlen endian gid
  810. return GIDMT_UNEXPECTED_ERROR;
  811. }
  812. le_gid=_htonl(le_gid);//use bigendian gid
  813. se_static_assert(sizeof(le_gid)==sizeof(gid));
  814. if(memcmp(&le_gid,&gid,sizeof(gid))!=0){
  815. return GIDMT_UNMATCHED;
  816. }
  817. return GIDMT_MATCHED;
  818. }
  819. aesm_error_t AESMLogic::report_attestation_status(
  820. uint8_t* platform_info, uint32_t platform_info_size,
  821. uint32_t attestation_status,
  822. uint8_t* update_info, uint32_t update_info_size)
  823. {
  824. AESM_DBG_INFO("report_attestation_status");
  825. AESMLogicLock lock(_pse_mutex);
  826. CHECK_LONG_TERM_PAIRING_STATUS;
  827. return PlatformInfoLogic::report_attestation_status(platform_info, platform_info_size, attestation_status, update_info, update_info_size);
  828. }
  829. ae_error_t AESMLogic::get_white_list_size_without_lock(uint32_t *white_list_cert_size)
  830. {
  831. uint32_t white_cert_size = 0;
  832. ae_error_t ae_ret = aesm_query_data_size(FT_PERSISTENT_STORAGE, AESM_WHITE_LIST_CERT_FID, &white_cert_size);
  833. if (AE_SUCCESS == ae_ret)
  834. {
  835. if (white_cert_size != 0){//file existing and not 0 size
  836. *white_list_cert_size = white_cert_size;
  837. return AE_SUCCESS;
  838. }
  839. else
  840. return AE_FAILURE;
  841. }
  842. else
  843. {
  844. return ae_ret;
  845. }
  846. }
  847. aesm_error_t AESMLogic::get_white_list_size(
  848. uint32_t* white_list_cert_size)
  849. {
  850. if (NULL == white_list_cert_size){
  851. return AESM_PARAMETER_ERROR;
  852. }
  853. CHECK_SERVICE_STATUS;
  854. AESMLogicLock lock(_le_mutex);
  855. CHECK_SERVICE_STATUS;
  856. ae_error_t ae_ret = get_white_list_size_without_lock(white_list_cert_size);
  857. if (AE_SUCCESS == ae_ret)
  858. return AESM_SUCCESS;
  859. else
  860. return AESM_UNEXPECTED_ERROR;
  861. }
  862. aesm_error_t AESMLogic::get_white_list(
  863. uint8_t *white_list_cert, uint32_t buf_size)
  864. {
  865. uint32_t white_cert_size=0;
  866. if (NULL == white_list_cert){
  867. return AESM_PARAMETER_ERROR;
  868. }
  869. CHECK_SERVICE_STATUS;
  870. AESMLogicLock lock(_le_mutex);
  871. CHECK_SERVICE_STATUS;
  872. ae_error_t ae_ret = get_white_list_size_without_lock(&white_cert_size);
  873. if (AE_SUCCESS != ae_ret)
  874. return AESM_UNEXPECTED_ERROR;
  875. if (white_cert_size != buf_size)
  876. {
  877. return AESM_PARAMETER_ERROR;
  878. }
  879. ae_ret = aesm_read_data(FT_PERSISTENT_STORAGE, AESM_WHITE_LIST_CERT_FID, white_list_cert, &white_cert_size);
  880. if (AE_SUCCESS != ae_ret){
  881. AESM_DBG_WARN("Fail to read white cert list file");
  882. return AESM_UNEXPECTED_ERROR;
  883. }
  884. return AESM_SUCCESS;
  885. }
  886. ae_error_t sgx_error_to_ae_error(sgx_status_t status)
  887. {
  888. if(SGX_ERROR_OUT_OF_MEMORY == status)
  889. return AE_OUT_OF_MEMORY_ERROR;
  890. if(SGX_SUCCESS == status)
  891. return AE_SUCCESS;
  892. return AE_FAILURE;
  893. }
  894. aesm_error_t AESMLogic::switch_extended_epid_group(
  895. uint32_t extended_epid_group_id
  896. )
  897. {
  898. AESM_DBG_INFO("AESMLogic::switch_extended_epid_group");
  899. ae_error_t ae_ret;
  900. if ((ae_ret = XEGDBlob::verify_xegd_by_xgid(extended_epid_group_id)) != AE_SUCCESS ||
  901. (ae_ret = EndpointSelectionInfo::verify_file_by_xgid(extended_epid_group_id)) != AE_SUCCESS){
  902. AESM_DBG_INFO("Fail to switch to extended epid group to %d due to XEGD blob for URL blob not available", extended_epid_group_id);
  903. return AESM_PARAMETER_ERROR;
  904. }
  905. ae_ret = set_global_extended_epid_group_id(extended_epid_group_id);
  906. if (ae_ret != AE_SUCCESS){
  907. AESM_DBG_INFO("Fail to switch to extended epid group %d", extended_epid_group_id);
  908. return AESM_UNEXPECTED_ERROR;
  909. }
  910. AESM_DBG_INFO("Succ to switch to extended epid group %d in data file, restart aesm required to use it", extended_epid_group_id);
  911. return AESM_SUCCESS;
  912. }
  913. aesm_error_t AESMLogic::get_extended_epid_group_id(
  914. uint32_t* extended_epid_group_id)
  915. {
  916. AESM_DBG_INFO("AESMLogic::get_extended_epid_group");
  917. if (NULL == extended_epid_group_id)
  918. {
  919. return AESM_PARAMETER_ERROR;
  920. }
  921. *extended_epid_group_id = get_active_extended_epid_group_id();
  922. return AESM_SUCCESS;
  923. }