Intel® Software Guard Extensions (Intel® SGX)
Use hardware-based isolation and memory encryption to provide more code protection in your solutions.

Intel SGX with Intrinsics

Rad_A_
Beginner
709 Views

Hi,

I'm importing a library to be compiled for SGX (to be loaded into an enclave). The thing is the library uses intrin.h which is not available in the SGX SDK. But I found sgx_intrin.h file and thought might replace the original header file. The problem is that sgx_intrin.h file has the following block:

/* Deprecated MSVC Intrinsics */
#if defined(_MSC_VER)
#include <intrin.h> /* Include MS intrin.h */
#include <sgx_cpuid.h>

It includes intrin.h file which does not exist in the SGX SDK. How can I resolve this issue? Should I just copy and paste the missing header file from MS VS include folder?

Thanks in advance.

Regards,
Rad

0 Kudos
1 Solution
Francisco_C_Intel
709 Views

You are linking the untrusted runtime library:

sgx_urts.lib

into your (trusted) enclave. This is why you are getting that error (sgx_urts.lib is not an actual static library, it's a stub library used to link against sgx_urts.dll)

View solution in original post

12 Replies
Surenthar_S_Intel
709 Views

Hi Red,
           The majority of Microsoft* Visual C++ intrinsics can be called inside the enclave, and an enclave project can include Microsoft* standard <intrin.h> directly with few restrictions. For example, you should not use intrinsics that generate instructions unsupported inside an enclave. All unsup-ported intrinsic functions generally fall into following categories:

  • I/O related functions.
  • Instructions requiring ring 0 privileges or can change privilege level.
  • OS or system related functions.
  • Intrinsics which are considered unprotected and encryption alternatives.

1. There are few requirements for including Microsoft* standard <intrin.h>:

  •  Add $(VCInstallDir)include;$(IncludePath) to Include Directories.
  •  Set Ignore Standard Include Path to No.

2. Use /Oi or #pragma intrinsic(…) to enable MSVC intrinsics.

The <sgx_intrin.h> also provides compile warnings for unsupported intrinsics.

NOTE:
The Intel® SGX SDK has stub implementations, sgx_intrin.h for the intrinsics that are not valid within an enclave. These stubs will cause a compiler warning when an unsupported instrinsic is used.

Refer page no 225 and Table 18 Unsupported MSVC Compiler Intrinsics in Intel-SGX-SDK-Users-Guide-for-Windows-OS.pdf

Thanks and Regards,
Surenthar Selvaraj

Rad_A_
Beginner
709 Views

Surenthar Selvaraj. (Intel) wrote:

Hi Red,
           The majority of Microsoft* Visual C++ intrinsics can be called inside the enclave, and an enclave project can include Microsoft* standard <intrin.h> directly with few restrictions. For example, you should not use intrinsics that generate instructions unsupported inside an enclave. All unsup-ported intrinsic functions generally fall into following categories:

  • I/O related functions.
  • Instructions requiring ring 0 privileges or can change privilege level.
  • OS or system related functions.
  • Intrinsics which are considered unprotected and encryption alternatives.

1. There are few requirements for including Microsoft* standard <intrin.h>:

  •  Add $(VCInstallDir)include;$(IncludePath) to Include Directories.
  •  Set Ignore Standard Include Path to No.

2. Use /Oi or #pragma intrinsic(…) to enable MSVC intrinsics.

The <sgx_intrin.h> also provides compile warnings for unsupported intrinsics.

NOTE:
The Intel® SGX SDK has stub implementations, sgx_intrin.h for the intrinsics that are not valid within an enclave. These stubs will cause a compiler warning when an unsupported instrinsic is used.

Refer page no 225 and Table 18 Unsupported MSVC Compiler Intrinsics in Intel-SGX-SDK-Users-Guide-for-Windows-OS.pdf

Thanks and Regards,
Surenthar Selvaraj

Thanks Surenthar for the reply. I tried it, but it failed with:

Error    2    error MSB3073: The command ""C:\Program Files (x86)\Intel\IntelSGXSDK\bin\win32\release\sgx_sign.exe" sign -key "enclave_private.pem" -enclave "enclave.dll" -out "enclave.signed.dll" -config "enclave.config.xml" :VCEnd" exited with code -1.

I found this post and tried to add only needed header files (not to add VC include folder to the project). So I created a separate folder in the IntelSGXSDK\include\ folder called "vs12" and added the following files:

ammintrin.h
ConcurrencySal.h
crtdefs.h
emmintrin.h
immintrin.h
intrin.h
mm3dnow.h
mmintrin.h
nmmintrin.h
pmmintrin.h
sal.h
setjmp.h
smmintrin.h
tmmintrin.h
vadefs.h
wmmintrin.h
xmmintrin.h

1. Then I found #include <malloc.h> in xmmintrin.h file. There is no such file in the SGX SDK and based on the post (mentioned above), I should not used the standard "malloc.h". Am I missing something?

2. Since I didn't need "malloc.h" functionalities, I commented the following lines in xmmintrin.h file (to be able to get the code compiled):

...

#ifndef _INC_MALLOC
/* pick up _mm_malloc() and _mm_free() */
//#include <malloc.h>
#endif  /* _INC_MALLOC */
#endif  /* __ICL */

...

#ifdef __ICL
//extern void* __cdecl _mm_malloc(size_t _Siz, size_t _Al);
//extern void __cdecl _mm_free(void *_P);
#endif  /* __ICL */

...

But still cannot get the project built (the error mentioned above). What does that error mean? How can I resolve it?

Thanks in advance.

Regards,
Rad

Surenthar_S_Intel
709 Views

Hi Rad,

Could you please share the code with us. 

Thanks and Regards,
Surenthar Selvaraj

Rad_A_
Beginner
709 Views
//Enclave1.cpp
#include "Enclave1_t.h"

#include "sgx_trts.h"

#include "sgx_intrin.h"

void foo () {
  int registers[4];

  __cpuid(registers, 1);
}

//---------------------------------------
//Enclave1.edl
enclave {
    trusted {
        public void foo ();
    };

    untrusted {
    };
};

With the mentioned configuration parameters (additional include directories, headers from VS2013, etc), and also one additional library "sgx_urts.lib" which is needed for "_sgx_oc_cpuidex".

The above generates the same error after compiling and linking.

Thanks.

Regards,
Rad

Francisco_C_Intel
709 Views

You could run:

"C:\Program Files (x86)\Intel\IntelSGXSDK\bin\win32\release\sgx_sign.exe" sign -key "enclave_private.pem" -enclave "enclave.dll" -out "enclave.signed.dll" -config "enclave.config.xml"

In a command prompt in the appropriate directory to get more information.

If compile and link completed then your enclave built properly, but signing the enclave failed. Usually those errors happen because you are trying to sign in "Release" mode instead of "Debug" or "Pre-release". Other times it happens because the config xml file specifies something that is not supported.

 

Rad_A_
Beginner
709 Views

FRANCISCO C. (Intel) wrote:

You could run:

"C:\Program Files (x86)\Intel\IntelSGXSDK\bin\win32\release\sgx_sign.exe" sign -key "enclave_private.pem" -enclave "enclave.dll" -out "enclave.signed.dll" -config "enclave.config.xml"

In a command prompt in the appropriate directory to get more information.

If compile and link completed then your enclave built properly, but signing the enclave failed. Usually those errors happen because you are trying to sign in "Release" mode instead of "Debug" or "Pre-release". Other times it happens because the config xml file specifies something that is not supported.

 

Thanks for the reply. The below is the output (didn't help me much to resolve the issue):

1>PostBuildEvent:
1>  Description: sign the enclave
1>EXEC : warning : undefined symbol detected.
1>  The input enclave file is not correct.
1>  Error happened while signing the enclave.
1>  <EnclaveConfiguration>
1>      <ProdID>0</ProdID>
1>      <ISVSVN>0</ISVSVN>
1>      <StackMaxSize>0x40000</StackMaxSize>
1>      <HeapMaxSize>0x100000</HeapMaxSize>
1>      <TCSNum>1</TCSNum>
1>      <TCSPolicy>1</TCSPolicy>
1>      <DisableDebug>0</DisableDebug>
1>      <MiscSelect>0</MiscSelect>
1>      <MiscMask>0xFFFFFFFF</MiscMask>
1>  </EnclaveConfiguration>
1>C:\Program Files (x86)\MSBuild\Microsoft.Cpp\v4.0\V120\Microsoft.CppCommon.targets(132,5): error MSB3073: The command ""C:\Program Files (x86)\Intel\IntelSGXSDK\bin\win32\release\sgx_sign.exe" sign -key "C:\works\trash\Enclave1\Enclave1\Enclave1_private.pem" -enclave "C:\works\trash\Enclave1\Debug\Enclave1.dll" -out "C:\works\trash\Enclave1\Debug\Enclave1.signed.dll" -config "C:\works\trash\Enclave1\Enclave1\Enclave1.config.xml"
1>C:\Program Files (x86)\MSBuild\Microsoft.Cpp\v4.0\V120\Microsoft.CppCommon.targets(132,5): error MSB3073: :VCEnd" exited with code -1.
1>
1>Build FAILED.

Any idea? Thanks.

Regards,
Rad

Francisco_C_Intel
709 Views

"warning : undefined symbol detected" corresponds to SGX_ERROR_UNDEFINED_SYMBOL.  From the SDK User's Guide:

SGX_ERROR_UNDEFINED_SYMBOL
The enclave contains an import table.
 

All libraries that are linked into an enclave need to be static libraries, which means that enclaves are not allowed to have import tables. Are any of the libraries you are trying to link in DLLs?

(Future versions of the tool may state "warning: enclave contains an import table" instead)
 

 

Rad_A_
Beginner
709 Views

FRANCISCO C. (Intel) wrote:

"warning : undefined symbol detected" corresponds to SGX_ERROR_UNDEFINED_SYMBOL.  From the SDK User's Guide:

SGX_ERROR_UNDEFINED_SYMBOL
The enclave contains an import table.
 

All libraries that are linked into an enclave need to be static libraries, which means that enclaves are not allowed to have import tables. Are any of the libraries you are trying to link in DLLs?

(Future versions of the tool may state "warning: enclave contains an import table" instead)
 

 

No. I created very simple enclave (as shown above it has nothing except one function). For the record, additional dependencies are:
sgx_trts.lib;sgx_tstdc.lib;sgx_tservice.lib;sgx_tcrypto.lib;sgx_tstdcxx.lib;sgx_urts.lib

Please note that I added some header files to the project (though didn't add any library or such from standard VS2013). Could the issue be because of the header files (listed in this comment)?

Regards,
Rad

Francisco_C_Intel
710 Views

You are linking the untrusted runtime library:

sgx_urts.lib

into your (trusted) enclave. This is why you are getting that error (sgx_urts.lib is not an actual static library, it's a stub library used to link against sgx_urts.dll)

View solution in original post

Rad_A_
Beginner
709 Views

FRANCISCO C. (Intel) wrote:

You are linking the untrusted runtime library:

sgx_urts.lib

into your (trusted) enclave. This is why you are getting that error (sgx_urts.lib is not an actual static library, it's a stub library used to link against sgx_urts.dll)

Thanks. I had to add it to be able to use sgx_intrin.h header (which needs intrin.h file from the standard include folder of VS2013), more specifically, if I didn't add it, I'd get the following error:

Error    1    error LNK2019: unresolved external symbol _sgx_oc_cpuidex referenced in function _sgx_cpuidex.    C:\works\trash\Enclave1\Enclave1\sgx_tstdc.lib(se_cpuid.obj)    Enclave1

Is there any other way to resolve this issue? Thanks.

Regards,
Rad

 

Rad_A_
Beginner
709 Views

There is no trusted version for this fuction (sgx_oc_cpuidex). Thus this function has to be called outside of enclave (OCALL) and I need to add it to the untrusted section of the main EDL file.

Is my understanding correct?

Regards,
Rad

Francisco_C_Intel
709 Views

You can take a look at the SampleEnclave to see how to import/call/link that function.

C:\Program Files (x86)\Intel\IntelSGXSDK\src\SampleEnclave\Enclave\TrustedLibrary\Libc.edl

 

Reply