diff --git a/Pal/src/host/Linux-SGX/gsgx.h b/Pal/src/host/Linux-SGX/gsgx.h new file mode 100644 index 0000000000..c7a7b25a90 --- /dev/null +++ b/Pal/src/host/Linux-SGX/gsgx.h @@ -0,0 +1,52 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +/* (C) Copyright 2020 Intel Corporation + * Dmitrii Kuvaiskii + */ + +#ifndef __ARCH_GSGX_H__ +#define __ARCH_GSGX_H__ + +#ifndef __packed +#define __packed __attribute__((packed)) +#endif + +#include +#include + +#include "sgx.h" + +#define GSGX_FILE "/dev/gsgx" +#define GSGX_MINOR MISC_DYNAMIC_MINOR + +/* Graphene needs the below subset of SGX instructions' return values */ +#ifndef SGX_INVALID_SIG_STRUCT +#define SGX_INVALID_SIG_STRUCT 1 +#endif + +#ifndef SGX_INVALID_ATTRIBUTE +#define SGX_INVALID_ATTRIBUTE 2 +#endif + +#ifndef SGX_INVALID_MEASUREMENT +#define SGX_INVALID_MEASUREMENT 4 +#endif + +#ifndef SGX_INVALID_SIGNATURE +#define SGX_INVALID_SIGNATURE 8 +#endif + +#ifndef SGX_INVALID_EINITTOKEN +#define SGX_INVALID_EINITTOKEN 16 +#endif + +#ifndef SGX_INVALID_CPUSVN +#define SGX_INVALID_CPUSVN 32 +#endif + +/* SGX_INVALID_LICENSE was renamed to SGX_INVALID_EINITTOKEN in SGX driver 2.1: + * https://github.com/intel/linux-sgx-driver/commit/a7997dafe184d7d527683d8d46c4066db205758d */ +#ifndef SGX_INVALID_LICENSE +#define SGX_INVALID_LICENSE SGX_INVALID_EINITTOKEN +#endif + +#endif /* __ARCH_GSGX_H__ */ diff --git a/Pal/src/host/Linux-SGX/link-intel-driver.py b/Pal/src/host/Linux-SGX/link-intel-driver.py new file mode 100755 index 0000000000..c0981b1fb4 --- /dev/null +++ b/Pal/src/host/Linux-SGX/link-intel-driver.py @@ -0,0 +1,59 @@ +#!/usr/bin/env python3 + +import sys, os, shutil + +DRIVER_VERSIONS = { + 'sgx_user.h': '/dev/isgx', + 'include/uapi/asm/sgx_oot.h': '/dev/sgx/enclave', + 'include/uapi/asm/sgx.h': '/dev/sgx/enclave', + 'sgx_in_kernel.h': '/dev/sgx/enclave', +} + +def find_intel_sgx_driver(): + """ + Graphene only needs one header from the Intel SGX Driver: + - sgx_user.h for non-DCAP, older version of the driver + (https://github.com/intel/linux-sgx-driver) + - include/uapi/asm/sgx_oot.h for DCAP 1.6+ version of the driver + (https://github.com/intel/SGXDataCenterAttestationPrimitives) + - include/uapi/asm/sgx.h for in-kernel 20+ version of the driver + (https://lore.kernel.org/linux-sgx/20190417103938.7762-1-jarkko.sakkinen@linux.intel.com/) + - default sgx_in_kernel.h for in-kernel 32+ version of the driver + (https://lore.kernel.org/linux-sgx/20200716135303.276442-1-jarkko.sakkinen@linux.intel.com) + + This function returns the required header from the SGX driver. + """ + isgx_driver_path = os.getenv("ISGX_DRIVER_PATH") + if not isgx_driver_path: + msg = 'Enter the Intel SGX driver dir with C headers (or press ENTER for in-kernel driver): ' + isgx_driver_path = os.path.expanduser(input(msg)) + + if not isgx_driver_path or isgx_driver_path.strip() == '': + # user did not specify any driver path, use default in-kernel driver's C header + isgx_driver_path = os.path.dirname(os.path.abspath(__file__)) + + for header_path, dev_path in DRIVER_VERSIONS.items(): + abs_header_path = os.path.abspath(os.path.join(isgx_driver_path, header_path)) + if os.path.exists(abs_header_path): + return abs_header_path, dev_path + + raise Exception("Could not find the header from the Intel SGX Driver") + + +def main(): + """ Find and copy header/device paths from Intel SGX Driver""" + header_path, dev_path = find_intel_sgx_driver() + + this_header_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'sgx.h') + shutil.copyfile(header_path, this_header_path) + + with open(this_header_path, 'a') as f: + f.write('\n\n#ifndef ISGX_FILE\n#define ISGX_FILE "%s"\n#endif\n' % dev_path) + if dev_path == '/dev/sgx' or dev_path == '/dev/sgx/enclave': + f.write('\n\n#ifndef SGX_DCAP\n#define SGX_DCAP 1\n#endif\n') + if dev_path == '/dev/sgx/enclave': + f.write('\n\n#ifndef SGX_DCAP_16_OR_LATER\n#define SGX_DCAP_16_OR_LATER 1\n#endif\n') + + +if __name__ == "__main__": + sys.exit(main()) diff --git a/Pal/src/host/Linux-SGX/sgx_in_kernel.h b/Pal/src/host/Linux-SGX/sgx_in_kernel.h new file mode 100644 index 0000000000..f14c2a03cf --- /dev/null +++ b/Pal/src/host/Linux-SGX/sgx_in_kernel.h @@ -0,0 +1,121 @@ +/* SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause) WITH Linux-syscall-note */ +/* + * Copyright(c) 2016-19 Intel Corporation. + */ + +/* TODO: Graphene must remove this file after Intel SGX driver is upstreamed + * and this header is distributed with the system. This header was tested + * with driver versions 32 and 36, it *may* be out of sync with newer + * versions. If possible, use the header found on the system instead of + * this one. */ + +#ifndef _UAPI_ASM_X86_SGX_H +#define _UAPI_ASM_X86_SGX_H + +#include +#include + +/** + * enum sgx_epage_flags - page control flags + * %SGX_PAGE_MEASURE: Measure the page contents with a sequence of + * ENCLS[EEXTEND] operations. + */ +enum sgx_page_flags { + SGX_PAGE_MEASURE = 0x01, +}; + +#define SGX_MAGIC 0xA4 + +#define SGX_IOC_ENCLAVE_CREATE \ + _IOW(SGX_MAGIC, 0x00, struct sgx_enclave_create) +#define SGX_IOC_ENCLAVE_ADD_PAGES \ + _IOWR(SGX_MAGIC, 0x01, struct sgx_enclave_add_pages) +#define SGX_IOC_ENCLAVE_INIT \ + _IOW(SGX_MAGIC, 0x02, struct sgx_enclave_init) +#define SGX_IOC_ENCLAVE_SET_ATTRIBUTE \ + _IOW(SGX_MAGIC, 0x03, struct sgx_enclave_set_attribute) + +/** + * struct sgx_enclave_create - parameter structure for the + * %SGX_IOC_ENCLAVE_CREATE ioctl + * @src: address for the SECS page data + */ +struct sgx_enclave_create { + __u64 src; +}; + +/** + * struct sgx_enclave_add_pages - parameter structure for the + * %SGX_IOC_ENCLAVE_ADD_PAGE ioctl + * @src: start address for the page data + * @offset: starting page offset + * @length: length of the data (multiple of the page size) + * @secinfo: address for the SECINFO data + * @flags: page control flags + * @count: number of bytes added (multiple of the page size) + */ +struct sgx_enclave_add_pages { + __u64 src; + __u64 offset; + __u64 length; + __u64 secinfo; + __u64 flags; + __u64 count; +}; + +/** + * struct sgx_enclave_init - parameter structure for the + * %SGX_IOC_ENCLAVE_INIT ioctl + * @sigstruct: address for the SIGSTRUCT data + */ +struct sgx_enclave_init { + __u64 sigstruct; +}; + +/** + * struct sgx_enclave_set_attribute - parameter structure for the + * %SGX_IOC_ENCLAVE_SET_ATTRIBUTE ioctl + * @attribute_fd: file handle of the attribute file in the securityfs + */ +struct sgx_enclave_set_attribute { + __u64 attribute_fd; +}; + +/** + * struct sgx_enclave_exception - structure to report exceptions encountered in + * __vdso_sgx_enter_enclave() + * + * @leaf: ENCLU leaf from \%eax at time of exception + * @trapnr: exception trap number, a.k.a. fault vector + * @error_code: exception error code + * @address: exception address, e.g. CR2 on a #PF + * @reserved: reserved for future use + */ +struct sgx_enclave_exception { + __u32 leaf; + __u16 trapnr; + __u16 error_code; + __u64 address; + __u64 reserved[2]; +}; + +/** + * typedef sgx_enclave_exit_handler_t - Exit handler function accepted by + * __vdso_sgx_enter_enclave() + * + * @rdi: RDI at the time of enclave exit + * @rsi: RSI at the time of enclave exit + * @rdx: RDX at the time of enclave exit + * @ursp: RSP at the time of enclave exit (untrusted stack) + * @r8: R8 at the time of enclave exit + * @r9: R9 at the time of enclave exit + * @tcs: Thread Control Structure used to enter enclave + * @ret: 0 on success (EEXIT), -EFAULT on an exception + * @e: Pointer to struct sgx_enclave_exception (as provided by caller) + */ +typedef int (*sgx_enclave_exit_handler_t)(long rdi, long rsi, long rdx, + long ursp, long r8, long r9, + void *tcs, int ret, + struct sgx_enclave_exception *e); + +#endif /* _UAPI_ASM_X86_SGX_H */