mirror of
https://github.com/corda/corda.git
synced 2025-01-27 14:49:35 +00:00
ENT-1263 - Use MRENCLAVE instead of enclave ID in create_thread (#487)
* ENT-1263 - Use MRENCLAVE instead of enclave_id for create_thread * ENT-1263 - Dedup dependencies in JAR * ENT-1263 - Ensure C++ 11 is used for enclave inspection tool * ENT-1263 - Throw exception if enclave ID mapping does not exist
This commit is contained in:
parent
e3c792c93d
commit
25bee1903a
2
sgx-jvm/jvm-enclave/.gitignore
vendored
Normal file
2
sgx-jvm/jvm-enclave/.gitignore
vendored
Normal file
@ -0,0 +1,2 @@
|
||||
test/tests
|
||||
tools/enclave-inspector
|
@ -30,7 +30,7 @@ add_custom_target(
|
||||
DEPENDS ${GENERATED_EDL_FILES}
|
||||
)
|
||||
|
||||
set(SOURCE_FILES sgx_utilities.cpp untrusted_start_thread.cpp untrusted_debug_print.cpp ${GENERATED_RPC_DIR}/java_u.c)
|
||||
set(SOURCE_FILES sgx_utilities.cpp untrusted_start_thread.cpp untrusted_debug_print.cpp enclave_map.cpp enclave_metadata.cpp ${GENERATED_RPC_DIR}/java_u.c)
|
||||
add_library(common OBJECT ${SOURCE_FILES})
|
||||
set_property(TARGET common PROPERTY POSITION_INDEPENDENT_CODE ON)
|
||||
target_include_directories(common PUBLIC ${SGX_SDK_INCLUDE} ${GENERATED_RPC_DIR})
|
||||
|
58
sgx-jvm/jvm-enclave/common/elf_types.h
Normal file
58
sgx-jvm/jvm-enclave/common/elf_types.h
Normal file
@ -0,0 +1,58 @@
|
||||
#ifndef __ELF_TYPES_H__
|
||||
#define __ELF_TYPES_H__
|
||||
|
||||
typedef uint64_t Elf64_Addr;
|
||||
typedef uint16_t Elf64_Quarter;
|
||||
typedef uint32_t Elf64_Half;
|
||||
typedef uint64_t Elf64_Off;
|
||||
typedef uint32_t Elf64_Word;
|
||||
typedef uint64_t Elf64_Xword;
|
||||
|
||||
#define ELFMAG0 0x7f // e_ident[EI_MAG0]
|
||||
#define ELFMAG1 'E' // e_ident[EI_MAG1]
|
||||
#define ELFMAG2 'L' // e_ident[EI_MAG2]
|
||||
#define ELFMAG3 'F' // e_ident[EI_MAG3]
|
||||
|
||||
#define EI_NIDENT 16 // Size of e_ident array
|
||||
#define EI_CLASS 4 // Class of machine
|
||||
#define ELFCLASSNONE 0 // Unknown class
|
||||
#define ELFCLASS32 1 // 32-bit architecture
|
||||
#define ELFCLASS64 2 // 64-bit architecture
|
||||
|
||||
typedef struct {
|
||||
unsigned char e_ident[EI_NIDENT]; // File identification
|
||||
Elf64_Quarter e_type; // File type
|
||||
Elf64_Quarter e_machine; // Machine architecture
|
||||
Elf64_Word e_version; // ELF format version
|
||||
Elf64_Addr e_entry; // Entry point
|
||||
Elf64_Off e_phoff; // Program header file offset
|
||||
Elf64_Off e_shoff; // Section header file offset
|
||||
Elf64_Word e_flags; // Architecture-specific flags
|
||||
Elf64_Quarter e_ehsize; // Size of ELF header in bytes
|
||||
Elf64_Quarter e_phentsize; // Size of program header entry
|
||||
Elf64_Quarter e_phnum; // Number of program header entries
|
||||
Elf64_Quarter e_shentsize; // Size of section header entry
|
||||
Elf64_Quarter e_shnum; // Number of section header entries
|
||||
Elf64_Quarter e_shstrndx; // Section name strings section
|
||||
} Elf64_Ehdr;
|
||||
|
||||
typedef struct {
|
||||
Elf64_Word sh_name; // Section name (index into section header string table)
|
||||
Elf64_Word sh_type; // Section type
|
||||
Elf64_Xword sh_flags; // Section flags
|
||||
Elf64_Addr sh_addr; // Address in memory image
|
||||
Elf64_Off sh_offset; // Offset in file
|
||||
Elf64_Xword sh_size; // Size in bytes
|
||||
Elf64_Word sh_link; // Index of a related section
|
||||
Elf64_Word sh_info; // Depends on section type
|
||||
Elf64_Xword sh_addralign; // Alignment in bytes
|
||||
Elf64_Xword sh_entsize; // Size of each entry in section
|
||||
} Elf64_Shdr;
|
||||
|
||||
typedef struct {
|
||||
Elf64_Half namesz; // Length of note name string
|
||||
Elf64_Half descsz; // Length of note description string
|
||||
Elf64_Half type; // Note type
|
||||
} Elf64_Note;
|
||||
|
||||
#endif /* __ELF_TYPES_H__ */
|
21
sgx-jvm/jvm-enclave/common/enclave_map.cpp
Normal file
21
sgx-jvm/jvm-enclave/common/enclave_map.cpp
Normal file
@ -0,0 +1,21 @@
|
||||
#include <cstring>
|
||||
#include <stdexcept>
|
||||
#include "enclave_map.h"
|
||||
|
||||
static enclave_map_t map;
|
||||
|
||||
void add_enclave_mapping(sgx_measurement_t *mr_enclave, sgx_enclave_id_t enclave_id) {
|
||||
// Note: The size of the enclave map is proportional to the number of unique
|
||||
// enclaves a system is dealing with. For the time being we don't envision this
|
||||
// number to be very big. Longer term, we might want to implement some form of
|
||||
// pruning to avoid old entries taking up unnecessary memory space.
|
||||
map[mr_enclave] = enclave_id;
|
||||
}
|
||||
|
||||
sgx_enclave_id_t get_enclave_id(sgx_measurement_t *mr_enclave) {
|
||||
auto result = map.find(mr_enclave);
|
||||
if (result == map.end()) {
|
||||
throw std::invalid_argument("no enclave ID associated with enclave measurement");
|
||||
}
|
||||
return result->second;
|
||||
}
|
21
sgx-jvm/jvm-enclave/common/enclave_map.h
Normal file
21
sgx-jvm/jvm-enclave/common/enclave_map.h
Normal file
@ -0,0 +1,21 @@
|
||||
#ifndef __ENCLAVE_MAP_H__
|
||||
#define __ENCLAVE_MAP_H__
|
||||
|
||||
#include <functional>
|
||||
#include <map>
|
||||
#include <sgx_eid.h>
|
||||
#include <sgx_report.h>
|
||||
|
||||
struct enclave_hash_comparer : public std::binary_function<const sgx_measurement_t*, const sgx_measurement_t*, bool> {
|
||||
public:
|
||||
bool operator() (const sgx_measurement_t* a, const sgx_measurement_t* b) const
|
||||
{ return memcmp(a->m, b->m, 32) < 0; }
|
||||
};
|
||||
|
||||
class enclave_map_t : public std::map<sgx_measurement_t*, sgx_enclave_id_t, enclave_hash_comparer> { };
|
||||
|
||||
void add_enclave_mapping(sgx_measurement_t *mr_enclave, sgx_enclave_id_t enclave_id);
|
||||
|
||||
sgx_enclave_id_t get_enclave_id(sgx_measurement_t *mr_enclave);
|
||||
|
||||
#endif /* __ENCLAVE_MAP_H__ */
|
127
sgx-jvm/jvm-enclave/common/enclave_metadata.cpp
Normal file
127
sgx-jvm/jvm-enclave/common/enclave_metadata.cpp
Normal file
@ -0,0 +1,127 @@
|
||||
#include <iostream>
|
||||
#include <cstddef>
|
||||
#include <cstring>
|
||||
|
||||
#include "enclave_metadata.h"
|
||||
#include "elf_types.h"
|
||||
#include "sgx_types.h"
|
||||
|
||||
static enclave_hash_result_t read_header(FILE *fp, Elf64_Ehdr *header) {
|
||||
if (0 != fseek(fp, 0, SEEK_SET)) {
|
||||
return EHR_ERROR_READ_FILE;
|
||||
}
|
||||
|
||||
size_t read = fread(header, sizeof(Elf64_Ehdr), 1, fp);
|
||||
if (0 == read) {
|
||||
return EHR_ERROR_READ_ELF_HEADER;
|
||||
}
|
||||
|
||||
if (header->e_ident[0] != ELFMAG0
|
||||
|| header->e_ident[1] != ELFMAG1
|
||||
|| header->e_ident[2] != ELFMAG2
|
||||
|| header->e_ident[3] != ELFMAG3) {
|
||||
return EHR_ERROR_NOT_ELF_FORMAT;
|
||||
}
|
||||
|
||||
if (header->e_ident[EI_CLASS] != ELFCLASS64) {
|
||||
return EHR_ERROR_NOT_ELF64_FORMAT;
|
||||
}
|
||||
|
||||
return EHR_SUCCESS;
|
||||
}
|
||||
|
||||
static enclave_hash_result_t find_section(FILE *fp, Elf64_Ehdr *header, const char *name, Elf64_Shdr *metadata_section) {
|
||||
fseek(fp, header->e_shoff, SEEK_SET);
|
||||
Elf64_Shdr *sections = static_cast<Elf64_Shdr*>(calloc(header->e_shnum, sizeof(Elf64_Shdr)));
|
||||
if (NULL == sections) {
|
||||
return EHR_ERROR_OUT_OF_MEMORY;
|
||||
}
|
||||
|
||||
if (header->e_shnum != fread(sections, sizeof(Elf64_Shdr), header->e_shnum, fp)) {
|
||||
free(sections);
|
||||
return EHR_ERROR_READ_SECTION_HEADERS;
|
||||
}
|
||||
|
||||
Elf64_Shdr *name_section = §ions[header->e_shstrndx];
|
||||
for (int i = 1; i < header->e_shnum; i++) { // Skip index 0, always empty
|
||||
char name[16];
|
||||
fseek(fp, name_section->sh_offset + sections[i].sh_name, SEEK_SET);
|
||||
fread(name, 1, 16, fp);
|
||||
if (0 == strncmp(name, ".note.sgxmeta", 16)) {
|
||||
memcpy(metadata_section, §ions[i], sizeof(Elf64_Shdr));
|
||||
free(sections);
|
||||
return EHR_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
free(sections);
|
||||
return EHR_ERROR_NO_SGX_META_DATA_SECTION;
|
||||
}
|
||||
|
||||
enclave_hash_result_t retrieve_enclave_hash(const char *path, uint8_t *enclave_hash) {
|
||||
FILE *fp = fopen(path, "rb");
|
||||
if (!fp) {
|
||||
return EHR_ERROR_READ_FILE;
|
||||
}
|
||||
|
||||
Elf64_Ehdr header;
|
||||
enclave_hash_result_t read_header_result = read_header(fp, &header);
|
||||
if (EHR_SUCCESS != read_header_result) {
|
||||
fclose(fp);
|
||||
return read_header_result;
|
||||
}
|
||||
|
||||
Elf64_Shdr section;
|
||||
enclave_hash_result_t find_section_result = find_section(fp, &header, ".note.sgxmeta", §ion);
|
||||
if (EHR_SUCCESS != find_section_result) {
|
||||
fclose(fp);
|
||||
return find_section_result;
|
||||
}
|
||||
|
||||
size_t metadata_offset = section.sh_offset;
|
||||
size_t metadata_align = section.sh_addralign;
|
||||
|
||||
Elf64_Note note;
|
||||
fseek(fp, section.sh_offset, SEEK_SET);
|
||||
fread(¬e, sizeof(Elf64_Note), 1, fp);
|
||||
|
||||
if (section.sh_size != ROUND_TO(sizeof(Elf64_Note) + note.namesz + note.descsz, section.sh_addralign)) {
|
||||
fclose(fp);
|
||||
return EHR_ERROR_INVALID_SECTION_SIZE;
|
||||
}
|
||||
|
||||
const char *meta_name = "sgx_metadata";
|
||||
const size_t meta_name_len = strlen(meta_name);
|
||||
char meta_name_buffer[16] = { 0 };
|
||||
|
||||
fseek(fp, section.sh_offset + sizeof(Elf64_Note), SEEK_SET);
|
||||
fread(meta_name_buffer, 1, 16, fp);
|
||||
|
||||
if (meta_name_len + 1 != note.namesz || 0 != strncmp(meta_name, meta_name_buffer, meta_name_len)) {
|
||||
fclose(fp);
|
||||
return EHR_ERROR_INVALID_SECTION_NAME;
|
||||
}
|
||||
|
||||
size_t meta_data_offset = section.sh_offset + sizeof(Elf64_Note) + note.namesz;
|
||||
metadata_t *metadata = static_cast<metadata_t*>(malloc(sizeof(metadata_t)));
|
||||
if (NULL == metadata) {
|
||||
fclose(fp);
|
||||
return EHR_ERROR_OUT_OF_MEMORY;
|
||||
}
|
||||
|
||||
fseek(fp, meta_data_offset, SEEK_SET);
|
||||
if (1 != fread(metadata, sizeof(metadata_t), 1, fp)) {
|
||||
free(metadata);
|
||||
fclose(fp);
|
||||
return EHR_ERROR_READ_META_DATA;
|
||||
}
|
||||
|
||||
if (NULL != enclave_hash) {
|
||||
memcpy(enclave_hash, metadata->enclave_css.body.enclave_hash, MRE_SIZE);
|
||||
}
|
||||
|
||||
free(metadata);
|
||||
fclose(fp);
|
||||
|
||||
return EHR_SUCCESS;
|
||||
}
|
20
sgx-jvm/jvm-enclave/common/enclave_metadata.h
Normal file
20
sgx-jvm/jvm-enclave/common/enclave_metadata.h
Normal file
@ -0,0 +1,20 @@
|
||||
#ifndef __ENCLAVE_METADATA_H__
|
||||
#define __ENCLAVE_METADATA_H__
|
||||
|
||||
typedef enum _enclave_hash_result_t {
|
||||
EHR_SUCCESS, // The hash of the enclave was retrieved successfully
|
||||
EHR_ERROR_READ_FILE, // Unable to read the file
|
||||
EHR_ERROR_READ_ELF_HEADER, // Unable to read the file header
|
||||
EHR_ERROR_NOT_ELF_FORMAT, // The file is not an ELF file
|
||||
EHR_ERROR_NOT_ELF64_FORMAT, // The file is an ELF file, but only 64-bit ELF files are supported
|
||||
EHR_ERROR_OUT_OF_MEMORY, // Unable to allocate memory
|
||||
EHR_ERROR_READ_SECTION_HEADERS, // Unable to read section headers from file
|
||||
EHR_ERROR_NO_SGX_META_DATA_SECTION, // Unable to find note section named ".note.sgxmeta"
|
||||
EHR_ERROR_INVALID_SECTION_NAME, // Invalid name of note section
|
||||
EHR_ERROR_INVALID_SECTION_SIZE, // Invalid size of note section
|
||||
EHR_ERROR_READ_META_DATA, // Unable to read meta data from file
|
||||
} enclave_hash_result_t;
|
||||
|
||||
extern "C" enclave_hash_result_t retrieve_enclave_hash(const char *path, uint8_t *enclave_hash);
|
||||
|
||||
#endif /* __ENCLAVE_METADATA_H__ */
|
@ -1,9 +1,10 @@
|
||||
enclave {
|
||||
from "sgx_tstdc.edl" import *;
|
||||
include "sgx_report.h"
|
||||
trusted {
|
||||
public void create_new_thread(unsigned int nonce);
|
||||
};
|
||||
untrusted {
|
||||
void request_new_thread(uint64_t enclave_id, uint32_t nonce);
|
||||
void request_new_thread(sgx_measurement_t mr_enclave, uint32_t nonce);
|
||||
};
|
||||
};
|
||||
|
81
sgx-jvm/jvm-enclave/common/sgx_types.h
Normal file
81
sgx-jvm/jvm-enclave/common/sgx_types.h
Normal file
@ -0,0 +1,81 @@
|
||||
#ifndef __SGX_TYPES_H__
|
||||
#define __SGX_TYPES_H__
|
||||
|
||||
#pragma pack(push, 1)
|
||||
|
||||
#define ROUND_TO(x, align) \
|
||||
(((x) + ((align)-1)) & ~((align)-1))
|
||||
|
||||
#define MRE_SIZE 32 // Size of MRENCLAVE (in bytes)
|
||||
#define SE_KEY_SIZE 384 // Size of keys (in bytes)
|
||||
#define SE_EXP_SIZE 4 // RSA public key exponent size in bytes
|
||||
|
||||
typedef struct {
|
||||
uint64_t flags;
|
||||
uint64_t xfrm;
|
||||
} sgx_attributes_t;
|
||||
|
||||
typedef uint32_t sgx_misc_select_t;
|
||||
|
||||
typedef struct {
|
||||
sgx_attributes_t secs_attr;
|
||||
sgx_misc_select_t misc_select;
|
||||
} sgx_misc_attribute_t;
|
||||
|
||||
typedef struct { // 128 bytes
|
||||
uint8_t header[12]; // (0) must be (06000000E100000000000100H)
|
||||
uint32_t type; // (12) bit 31: 0 = prod, 1 = debug; Bit 30-0: Must be zero
|
||||
uint32_t module_vendor; // (16) Intel=0x8086, ISV=0x0000
|
||||
uint32_t date; // (20) build date as yyyymmdd
|
||||
uint8_t header2[16]; // (24) must be (01010000600000006000000001000000H)
|
||||
uint32_t hw_version; // (40) For Launch Enclaves: HWVERSION != 0. Others, HWVERSION = 0
|
||||
uint8_t reserved[84]; // (44) Must be 0
|
||||
} css_header_t;
|
||||
|
||||
typedef struct { // 772 bytes
|
||||
uint8_t modulus[SE_KEY_SIZE]; // (128) Module Public Key (keylength=3072 bits)
|
||||
uint8_t exponent[SE_EXP_SIZE]; // (512) RSA Exponent = 3
|
||||
uint8_t signature[SE_KEY_SIZE]; // (516) Signature over Header and Body
|
||||
} css_key_t;
|
||||
|
||||
typedef struct { // 128 bytes
|
||||
sgx_misc_select_t misc_select; // (900) The MISCSELECT that must be set
|
||||
sgx_misc_select_t misc_mask; // (904) Mask of MISCSELECT to enforce
|
||||
uint8_t reserved[20]; // (908) Reserved. Must be 0.
|
||||
sgx_attributes_t attributes; // (928) Enclave Attributes that must be set
|
||||
sgx_attributes_t attribute_mask; // (944) Mask of Attributes to Enforce
|
||||
uint8_t enclave_hash[MRE_SIZE]; // (960) MRENCLAVE - (32 bytes)
|
||||
uint8_t reserved2[32]; // (992) Must be 0
|
||||
uint16_t isv_prod_id; // (1024) ISV assigned Product ID
|
||||
uint16_t isv_svn; // (1026) ISV assigned SVN
|
||||
} css_body_t;
|
||||
|
||||
typedef struct { // 780 bytes
|
||||
uint8_t reserved[12]; // (1028) Must be 0
|
||||
uint8_t q1[SE_KEY_SIZE]; // (1040) Q1 value for RSA Signature Verification
|
||||
uint8_t q2[SE_KEY_SIZE]; // (1424) Q2 value for RSA Signature Verification
|
||||
} css_buffer_t;
|
||||
|
||||
typedef struct { // 1808 bytes
|
||||
css_header_t header; // (0)
|
||||
css_key_t key; // (128)
|
||||
css_body_t body; // (900)
|
||||
css_buffer_t buffer; // (1028)
|
||||
} enclave_css_t;
|
||||
|
||||
typedef struct {
|
||||
uint64_t magic_num; // The magic number identifying the file as a signed enclave image
|
||||
uint64_t version; // The metadata version
|
||||
uint32_t size; // The size of this structure
|
||||
uint32_t tcs_policy; // TCS management policy
|
||||
uint32_t ssa_frame_size; // The size of SSA frame in page
|
||||
uint32_t max_save_buffer_size; // Max buffer size is 2632
|
||||
uint32_t desired_misc_select;
|
||||
uint32_t tcs_min_pool; // TCS min pool*/
|
||||
uint64_t enclave_size; // enclave virtual size
|
||||
sgx_attributes_t attributes; // XFeatureMask to be set in SECS.
|
||||
enclave_css_t enclave_css; // The enclave signature
|
||||
} metadata_t;
|
||||
|
||||
|
||||
#endif /* __SGX_TYPES_H__ */
|
@ -2,20 +2,22 @@
|
||||
#include <pthread.h>
|
||||
#include "java_u.h"
|
||||
#include "sgx_utilities.h"
|
||||
#include "enclave_map.h"
|
||||
|
||||
extern "C" {
|
||||
struct new_thread_data {
|
||||
sgx_enclave_id_t enclave_id;
|
||||
sgx_measurement_t mr_enclave;
|
||||
unsigned int nonce;
|
||||
};
|
||||
void *create_new_enclave_thread(void *param) {
|
||||
auto thread_data = (new_thread_data*) param;
|
||||
CHECK_SGX(create_new_thread(thread_data->enclave_id, thread_data->nonce));
|
||||
sgx_enclave_id_t enclave_id = get_enclave_id(&thread_data->mr_enclave);
|
||||
CHECK_SGX(create_new_thread(enclave_id, thread_data->nonce));
|
||||
delete thread_data;
|
||||
}
|
||||
void request_new_thread(sgx_enclave_id_t enclave_id, unsigned int nonce) {
|
||||
void request_new_thread(sgx_measurement_t mr_enclave, unsigned int nonce) {
|
||||
pthread_t enclave_thread;
|
||||
new_thread_data *thread_data = new new_thread_data { enclave_id, nonce };
|
||||
new_thread_data *thread_data = new new_thread_data { mr_enclave, nonce };
|
||||
int ret = pthread_create(&enclave_thread, NULL, create_new_enclave_thread, (void *)thread_data);
|
||||
assert(!ret);
|
||||
}
|
||||
|
@ -2,6 +2,7 @@
|
||||
#include <sgx_thread_mutex_guard.h>
|
||||
#include <sgx_thread_completion.h>
|
||||
#include <sgx_trts.h>
|
||||
#include <sgx_utils.h>
|
||||
#include <java_t.h>
|
||||
|
||||
#include "aex_assert.h"
|
||||
@ -28,7 +29,21 @@ struct ThreadMutexInit {
|
||||
};
|
||||
static ThreadMutexInit _thread_mutex_init;
|
||||
|
||||
static sgx_status_t get_mr_enclave(sgx_measurement_t *mr_enclave) {
|
||||
sgx_report_t report;
|
||||
sgx_status_t ret = sgx_create_report(NULL, NULL, &report);
|
||||
if (ret == SGX_SUCCESS) {
|
||||
memcpy(mr_enclave, &report.body.mr_enclave, sizeof(sgx_measurement_t));
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
thread_data_t *start_thread(void (*routine)(void *), void *param, sgx_thread_completion *thread_completed) {
|
||||
sgx_measurement_t mr_enclave = { 0 };
|
||||
if (SGX_SUCCESS != get_mr_enclave(&mr_enclave)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
nonce_t nonce;
|
||||
aex_assert(SGX_SUCCESS == sgx_read_rand((unsigned char*)&nonce, sizeof(nonce)));
|
||||
sgx_thread_cond_t thread_started;
|
||||
@ -47,11 +62,7 @@ thread_data_t *start_thread(void (*routine)(void *), void *param, sgx_thread_com
|
||||
aex_assert(new_thread_map.find(nonce) == new_thread_map.end());
|
||||
new_thread_map[nonce] = thread_init_data;
|
||||
}
|
||||
|
||||
// TODO use MRENCLAVE instead of enclave_id (this is currently not used)
|
||||
uint64_t enclave_id = 0L;
|
||||
|
||||
request_new_thread(enclave_id, nonce);
|
||||
request_new_thread(mr_enclave, nonce);
|
||||
sgx_thread_cond_wait(&thread_started, &thread_started_mutex);
|
||||
sgx_thread_mutex_guard started_thread_data_map_guard(&started_thread_data_map_mutex);
|
||||
auto thread_data_iter = started_thread_data_map.find(nonce);
|
||||
|
@ -2,6 +2,8 @@
|
||||
|
||||
#include "java_u.h"
|
||||
#include "sgx_utilities.h"
|
||||
#include "enclave_map.h"
|
||||
#include "enclave_metadata.h"
|
||||
#include <sgx_urts.h>
|
||||
|
||||
extern "C" {
|
||||
@ -14,7 +16,14 @@ JNIEXPORT jstring JNICALL Java_com_r3_enclaves_txverify_NativeSgxApi_verify(JNIE
|
||||
const char *enclave_path_sz = env->GetStringUTFChars(enclave_path, NULL);
|
||||
jbyte *transaction_bytes = env->GetByteArrayElements(transaction, NULL);
|
||||
|
||||
sgx_measurement_t mr_enclave;
|
||||
enclave_hash_result_t hash_result = retrieve_enclave_hash(enclave_path_sz, mr_enclave.m);
|
||||
if (EHR_SUCCESS != hash_result) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
CHECK_SGX(sgx_create_enclave(enclave_path_sz, SGX_DEBUG_FLAG, &token, &updated, &enclave_id, NULL));
|
||||
add_enclave_mapping(&mr_enclave, enclave_id);
|
||||
|
||||
char error[1024] = {0};
|
||||
printf("Array length %d\n", env->GetArrayLength(transaction));
|
||||
|
@ -4,13 +4,25 @@
|
||||
#include <fstream>
|
||||
#include "sgx_utilities.h"
|
||||
#include "java_u.h"
|
||||
#include "enclave_map.h"
|
||||
#include "enclave_metadata.h"
|
||||
|
||||
static sgx_measurement_t mr_enclave;
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
sgx_launch_token_t token = {0};
|
||||
sgx_enclave_id_t enclave_id = {0};
|
||||
int updated = 0;
|
||||
|
||||
CHECK_SGX(sgx_create_enclave("../../enclave/build/cordaenclave.signed.so", SGX_DEBUG_FLAG, &token, &updated, &enclave_id, NULL));
|
||||
const char *enclave_path = "../../enclave/build/cordaenclave.signed.so";
|
||||
enclave_hash_result_t hash_result = retrieve_enclave_hash(enclave_path, mr_enclave.m);
|
||||
if (EHR_SUCCESS != hash_result) {
|
||||
printf("Unable to retrieve MRENCLAVE from enclave\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
CHECK_SGX(sgx_create_enclave(enclave_path, SGX_DEBUG_FLAG, &token, &updated, &enclave_id, NULL));
|
||||
add_enclave_mapping(&mr_enclave, enclave_id);
|
||||
|
||||
if (argc < 2) {
|
||||
printf("Usage: <executable> /path/to/req/file\n");
|
||||
|
18
sgx-jvm/jvm-enclave/test/Makefile
Normal file
18
sgx-jvm/jvm-enclave/test/Makefile
Normal file
@ -0,0 +1,18 @@
|
||||
.PHONY: all test clean
|
||||
|
||||
LIBDIR = ../common
|
||||
SDKDIR = ../../linux-sgx/common/inc
|
||||
SOURCE = tests.cpp ${LIBDIR}/enclave_map.cpp
|
||||
HEADERS = ${LIBDIR}/enclave_map.h ${LIBDIR}/elf_types.h ${LIBDIR}/sgx_types.h
|
||||
RESULT = tests
|
||||
|
||||
all: ${RESULT}
|
||||
|
||||
${RESULT}: ${SOURCE} ${HEADERS}
|
||||
g++ -std=c++11 -o $@ -I${LIBDIR} -I${SDKDIR} ${SOURCE}
|
||||
|
||||
test: ${RESULT}
|
||||
./${RESULT}
|
||||
|
||||
clean:
|
||||
@rm -f ${RESULT}
|
12796
sgx-jvm/jvm-enclave/test/catch.hpp
Normal file
12796
sgx-jvm/jvm-enclave/test/catch.hpp
Normal file
File diff suppressed because it is too large
Load Diff
103
sgx-jvm/jvm-enclave/test/tests.cpp
Normal file
103
sgx-jvm/jvm-enclave/test/tests.cpp
Normal file
@ -0,0 +1,103 @@
|
||||
#define CATCH_CONFIG_MAIN
|
||||
#include "catch.hpp"
|
||||
|
||||
#include "enclave_map.h"
|
||||
|
||||
SCENARIO(
|
||||
"enclave identifiers can be looked up based on enclaves' measurements",
|
||||
"[enclave-map]"
|
||||
) {
|
||||
|
||||
GIVEN( "an empty map" ) {
|
||||
enclave_map_t map;
|
||||
|
||||
REQUIRE( map.size() == 0 );
|
||||
|
||||
WHEN( "a new entry gets added" ) {
|
||||
sgx_measurement_t mr_enclave = { 0 };
|
||||
sgx_enclave_id_t enclave_id = 1L;
|
||||
map[&mr_enclave] = enclave_id;
|
||||
|
||||
THEN( "the size of the map increases" ) {
|
||||
REQUIRE( map.size() == 1 );
|
||||
}
|
||||
|
||||
THEN( "the mapping can be found" ) {
|
||||
auto result = map.find(&mr_enclave);
|
||||
REQUIRE( result != map.end() );
|
||||
}
|
||||
|
||||
THEN( "the mapping returns the correct value" ) {
|
||||
auto result = map.find(&mr_enclave);
|
||||
REQUIRE( result->second == 1L );
|
||||
}
|
||||
|
||||
THEN( "a non-existent mapping cannot be looked up" ) {
|
||||
sgx_measurement_t non_existent_mr_enclave = { 1 };
|
||||
auto result = map.find(&non_existent_mr_enclave);
|
||||
REQUIRE( result == map.end() );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
GIVEN( "a populated map" ) {
|
||||
enclave_map_t map;
|
||||
sgx_measurement_t mr_enclave_orig = { 0 };
|
||||
sgx_enclave_id_t enclave_id = 1L;
|
||||
map[&mr_enclave_orig] = enclave_id;
|
||||
|
||||
REQUIRE( map.size() == 1 );
|
||||
|
||||
WHEN( "a new entry gets added" ) {
|
||||
sgx_measurement_t mr_enclave = { 1 };
|
||||
sgx_enclave_id_t enclave_id = 2L;
|
||||
map[&mr_enclave] = enclave_id;
|
||||
|
||||
THEN( "the size of the map increases" ) {
|
||||
REQUIRE( map.size() == 2 );
|
||||
}
|
||||
|
||||
THEN( "the mapping can be found" ) {
|
||||
auto result = map.find(&mr_enclave);
|
||||
REQUIRE( result != map.end() );
|
||||
}
|
||||
|
||||
THEN( "the mapping returns the correct value" ) {
|
||||
auto result = map.find(&mr_enclave);
|
||||
REQUIRE( result->second == 2L );
|
||||
}
|
||||
|
||||
THEN( "the value for the pre-existing entry is correct" ) {
|
||||
auto result = map.find(&mr_enclave_orig);
|
||||
REQUIRE( result->second == 1L );
|
||||
}
|
||||
|
||||
THEN( "a non-existent mapping cannot be looked up" ) {
|
||||
sgx_measurement_t non_existent_mr_enclave = { 2 };
|
||||
auto result = map.find(&non_existent_mr_enclave);
|
||||
REQUIRE( result == map.end() );
|
||||
}
|
||||
}
|
||||
|
||||
WHEN( "a existing entry gets overwritten" ) {
|
||||
sgx_measurement_t mr_enclave = { 0 };
|
||||
sgx_enclave_id_t enclave_id = 2L;
|
||||
map[&mr_enclave] = enclave_id;
|
||||
|
||||
THEN( "the size of the map stays the same" ) {
|
||||
REQUIRE( map.size() == 1 );
|
||||
}
|
||||
|
||||
THEN( "the mapping can be found" ) {
|
||||
auto result = map.find(&mr_enclave);
|
||||
REQUIRE( result != map.end() );
|
||||
}
|
||||
|
||||
THEN( "the mapping returns the correct value" ) {
|
||||
auto result = map.find(&mr_enclave);
|
||||
REQUIRE( result->second == 2L );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
14
sgx-jvm/jvm-enclave/tools/Makefile
Normal file
14
sgx-jvm/jvm-enclave/tools/Makefile
Normal file
@ -0,0 +1,14 @@
|
||||
.PHONY: all clean
|
||||
|
||||
LIBDIR = ../common
|
||||
SOURCE = enclave-inspector.cpp ${LIBDIR}/enclave_metadata.cpp
|
||||
HEADERS = ${LIBDIR}/enclave_metadata.h ${LIBDIR}/elf_types.h ${LIBDIR}/sgx_types.h
|
||||
RESULT = enclave-inspector
|
||||
|
||||
all: ${RESULT}
|
||||
|
||||
${RESULT}: ${SOURCE} ${HEADERS}
|
||||
g++ -std=c++11 -o $@ ${SOURCE}
|
||||
|
||||
clean:
|
||||
@rm -f ${RESULT}
|
48
sgx-jvm/jvm-enclave/tools/enclave-inspector.cpp
Normal file
48
sgx-jvm/jvm-enclave/tools/enclave-inspector.cpp
Normal file
@ -0,0 +1,48 @@
|
||||
#include <iostream>
|
||||
#include <iomanip>
|
||||
#include <cstddef>
|
||||
|
||||
#include "../common/enclave_metadata.h"
|
||||
|
||||
using namespace std;
|
||||
|
||||
static const char *status_messages[] = {
|
||||
"Success",
|
||||
"Unable to read the file",
|
||||
"Unable to read the file header",
|
||||
"The file is not an ELF file",
|
||||
"The file is an ELF file, but only 64-bit ELF files are supported",
|
||||
"Unable to allocate memory",
|
||||
"Unable to read section headers from file",
|
||||
"Unable to find note section named \".note.sgxmeta\"",
|
||||
"Invalid name of note section",
|
||||
"Invalid size of note section",
|
||||
"Unable to read meta data from file",
|
||||
};
|
||||
|
||||
static void print_hex(uint8_t *buffer, size_t len) {
|
||||
for (int i = 0; i < len; i++) {
|
||||
cout << setfill('0') << setw(2) << setbase(16) << static_cast<int>(buffer[i]) << " ";
|
||||
}
|
||||
cout << endl;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
if (argc != 2) {
|
||||
cout << "SGX Enclave Inspector" << endl;
|
||||
cout << "Usage: " << argv[0] << " <enclave-object>" << endl;
|
||||
return 1;
|
||||
}
|
||||
|
||||
uint8_t enclave_hash[32] = { 0 };
|
||||
enclave_hash_result_t result = retrieve_enclave_hash(argv[1], enclave_hash);
|
||||
|
||||
cout << "Outcome: " << status_messages[result] << endl;
|
||||
if (EHR_SUCCESS == result) {
|
||||
cout << " Path = " << argv[1] << endl;
|
||||
cout << " Hash = ";
|
||||
print_hex(enclave_hash, 32);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
@ -57,6 +57,11 @@ dependencies {
|
||||
}
|
||||
|
||||
jar {
|
||||
|
||||
// De-duplicate dependencies - otherwise, they will appear multiple times in the resulting JAR file, which in turn
|
||||
// will confuse ProGuard in the processing step in sgx-jvm/jvm-enclave.
|
||||
duplicatesStrategy = DuplicatesStrategy.EXCLUDE
|
||||
|
||||
from '../node/capsule/NOTICE' // Copy CDDL notice
|
||||
// Create a fat jar by packing all deps into the output
|
||||
from {
|
||||
|
Loading…
x
Reference in New Issue
Block a user