Search code examples
makefilecmakesgx

using CMake to complie cause SGX_ERROR_UNEXPECTED?


I am trying to learn intel sgx sdk recently.

Today i found a problem in my code and can not find any explain in intel DOC or WEB.

The code will return SGX_ERROR_UNEXPECTED when i call sgx_create_enclave in some situations. I think there are something wrong in my CMakeLists.txt( I use cmake to compile the untrusted part in my project), because code run correctly when i use the template Makefile in sdk example to compile. More details blow:

code will run success under these situations:

  * compile with Makefile

  * compile with cmake and comment out app.cpp:21

code will return error under this situation:

  * compile with cmake and do not comment out app.cpp:21

code available here (i have remove all unnecessary code): https://github.com/chilogen/workspace/tree/master/error/SimpleEnclave

app.cpp

#include "enclave_u.h"
#include <sgx_urts.h>
#include <sgx_uae_service.h>
#include <sgx_ukey_exchange.h>
#include <iostream>
using  namespace std;

class testClass {
public:
      sgx_launch_token_t _token = {0};
      sgx_enclave_id_t _eid;
      sgx_ra_context_t _ctx;
      void init_enclave();
      bool request(uint8_t *src, uint32_t srcLen, uint8_t *cmac);
      //will set _ctx here
      //void do_attestation();
}x;

bool testClass::request(uint8_t *src, uint32_t srcLen, uint8_t *cmac) {
    sgx_status_t retval,status;
    status = ecall_calcmac(_eid, &retval,&_ctx, SGX_RA_KEY_SK, src, srcLen, cmac);
    return true;
}

void testClass::init_enclave(){
    sgx_enclave_id_t global_eid;
    sgx_launch_token_t token={0};
    sgx_status_t ret;
    int updated=0;
    ret=sgx_create_enclave("enclave.signed.so",SGX_DEBUG_FLAG, \
                        &token,&updated,&global_eid,NULL);

    if(ret!=SGX_SUCCESS){
        std::cout<<"error init enclavedsfdsf\n";
        printf("%08x\n",ret);
        exit(1);
    }
}

int main(){
    x.init_enclave();
    return 0;
}

CMakeLists.txt

include_directories (/opt/intel/sgxsdk/include)
link_directories (/opt/intel/sgxsdk/lib64)
add_library (enclave_untrusted enclave_u.c)
add_executable (app app.cpp)
target_link_libraries (app enclave_untrusted sgx_ukey_exchange sgx_urts sgx_uae_service pthread)

Makefile (I think this is important part, if you don't know well at intel sgx, than you can still examine the different between CMakeLists.txt and Makefile)

## SGX SDK Settings
SGX_SDK ?= /opt/intel/sgxsdk

SGX_LIBRARY_PATH := $(SGX_SDK)/lib64
SGX_ENCLAVE_SIGNER := $(SGX_SDK)/bin/x64/sgx_sign
SGX_EDGER8R := $(SGX_SDK)/bin/x64/sgx_edger8r

######## App Settings ########

App_Include_Paths := -I$(SGX_SDK)/include 

App_Link_Flags := -L /opt/intel/sgxsdk/lib64 -lsgx_urts -lsgx_ukey_exchange -lsgx_uae_service  -pthread 


.PHONY: all
all: app

######## App Objects ########

enclave_u.c: $(SGX_EDGER8R) enclave.edl
    @$(SGX_EDGER8R) --untrusted enclave.edl --search-path $(SGX_SDK)/include
    @echo "GEN  =>  $@"

enclave_u.o: enclave_u.c
    @$(CC) $(App_Include_Paths) -c $< -o $@
    @echo "CC   <=  $<"

app.o: app.cpp
    @$(CXX) $(App_Include_Paths) -c $< -o $@ 
    @echo "CXX  <=  $<"

app: app.o enclave_u.o
    @$(CXX) $^ -o $@ $(App_Link_Flags)
    @echo "LINK =>  $@"

.PHONY: clean

clean:
    @rm -f *.o app

update : compile.sh

gcc -c -I /opt/intel/sgxsdk/include/ -o enclave_u.o enclave_u.c

g++ -c  app.cpp -o app.o -I /opt/intel/sgxsdk/include/

g++ -o app app.o enclave_u.o -L /opt/intel/sgxsdk/lib64 -lsgx_urts -lsgx_ukey_exchange -lsgx_uae_service  -pthread

So, what is wrong in my code (or CMakeLists.txt), how should i do?

I will be so thankful if your get me some idea about it.


Solution

  • Try using the target based API instead of the directory based:

    add_library (enclave_untrusted enclave_u.c)
    add_executable (app app.cpp)
    
    target_include_directories (enclave_untrusted PUBLIC /opt/intel/sgxsdk/include)
    
    target_link_libraries (enclave_untrusted PUBLIC
        "/opt/intel/sgxsdk/lib64/libsgx_urts.a"
        "/opt/intel/sgxsdk/lib64/libsgx_ukey_exchange.a"
        "/opt/intel/sgxsdk/lib64/libsgx_uae_service.a"
    )
    target_link_libraries (app PRIVATE enclave_untrusted pthread)
    

    But I would advise using an appropriated CMake library, like SGX-CMake