diff --git a/C/Makefile b/C/Makefile index 50a29bfab..fd8f5e16f 100644 --- a/C/Makefile +++ b/C/Makefile @@ -63,6 +63,7 @@ update_disk: echo "Building tychools" cargo build --manifest-path $(TYCHOOLS_PATH)/Cargo.toml --release --target=riscv64gc-unknown-linux-gnu --config target.riscv64gc-unknown-linux-gnu.linker=\"riscv64-unknown-linux-gnu-gcc\" make ARCH=riscv -B -C libraries/sdktyche/example/simple-enclave install_disk + make ARCH=riscv -B -C libraries/sdktyche/example/enclave_rot_riscv install_disk cp scripts/riscv64_install_drivers.sh /tmp/ubuntu_riscv_mount/tyche cp scripts/run_eapp.sh /tmp/ubuntu_riscv_mount/tyche cp $(TYCHOOLS_RISCV_PATH)/tychools $(PROGRAMGS_PATH)/tychools diff --git a/C/build_riscv.sh b/C/build_riscv.sh new file mode 100755 index 000000000..d97a2f307 --- /dev/null +++ b/C/build_riscv.sh @@ -0,0 +1,3 @@ +make ARCH=riscv ubuntu_mount || exit +make ARCH=riscv update_disk +make ARCH=riscv ubuntu_umount diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/.gitignore b/C/libraries/sdktyche/example/enclave_rot_riscv/.gitignore new file mode 100644 index 000000000..308b9d249 --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/.gitignore @@ -0,0 +1,4 @@ +app +enclave +simple_enclave +enclave_iso \ No newline at end of file diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/Makefile b/C/libraries/sdktyche/example/enclave_rot_riscv/Makefile new file mode 100644 index 000000000..906d4afa8 --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/Makefile @@ -0,0 +1,139 @@ +all: rot_enclave + +GCC ?=gcc +KVM ?=1 + +ifeq ($(ARCH), riscv) + GCC = riscv64-unknown-linux-gnu-gcc + KVM = 0 +endif + +ifeq ($(KVM), 1) + LOADER_BACKEND = -DRUN_WITH_KVM=1 +endif + + +## ————————————————————————————————— Paths —————————————————————————————————— ## +LIB_PATH=../../../ +LIB_DRIVER=../../../../../linux/drivers/tyche/libraries/ +DRIVERS_PATH=../../../../../linux/drivers/ +LINKER_SCRIPT=../../../../../configs/riscv-linker-script-domain.x + +## ——————————————————————————————— Libraries ———————————————————————————————— ## +SDK=$(LIB_PATH)/sdktyche +DLL_LIB= $(LIB_DRIVER)/dll +CAPA_LIB=$(LIB_DRIVER)/capabilities +COMMON_LIB=$(LIB_DRIVER)/common +ELF64=$(LIB_PATH)/elf64 +PTS=$(LIB_PATH)/pts +DRIVER=$(DRIVERS_PATH)/tyche +CONTALLOC=$(DRIVERS_PATH)/contalloc + +## ——————————————————————— Untrusted code and headers ——————————————————————— ## +CODE_UNTRUSTED=$(wildcard untrusted/*.c) +HDRS_UNTRUSTED=$(wildcard include/*.h) + +## ———————————————————————— Trusted code and headers ———————————————————————— ## +CODE_TRUSTED=$(wildcard trusted/*.c) +HDRS_TRUSTED=$(wildcard include/*.h) + +## ———————————————————————— Runtime code and headers ———————————————————————— ## +ifeq ($(ARCH), x86) +CODE_RUNTIME = $(wildcard $(SDK)/runtime/*.c) $(wildcard $(SDK)/runtime/asm.S) +HDRS_RUNTIME = $(wildcard $(SDK)/include/*.h) +else ifeq ($(ARCH), riscv) +CODE_RUNTIME = $(wildcard $(SDK)/runtime/*.c) $(wildcard $(SDK)/runtime/riscv_asm.S) +HDRS_RUNTIME = $(wildcard $(SDK)/include/*.h) +endif +# ———————————————————————— Code capabilities library ————————————————————————— # +CODE_CAPAS=$(wildcard $(CAPA_LIB)/src/*.c) +## ———————————————————————— Loader code and headers ————————————————————————— ## +CODE_LOADER=$(wildcard $(SDK)/loader/*.c) $(wildcard $(SDK)/loader/*.S) +HDRS_LOADER=$(wildcard $(SDK)/include/*.h) + +ifeq ($(KVM), 1) + CODE_LOADER+=$(SDK)/loader/backends/back_kvm.c +else + CODE_LOADER+=$(SDK)/loader/backends/back_tyche.c +endif + +## ————————————————————————— ELF64 code and headers ————————————————————————— ## +CODE_ELF64=$(wildcard $(ELF64)/src/*.c) +HDRS_ELF64=$(wildcard $(ELF64)/include/*.h) + +## —————————————————————— Page table code and headers ——————————————————————— ## +CODE_PTS=$(wildcard $(PTS)/src/*.c) +HDRS_PTS=$(wildcard $(PTS)/include/*.h) + +## —————————————————————— Application code and headers —————————————————————— ## +CODE_APP=$(CODE_ELF64) $(CODE_PTS) $(CODE_LOADER) $(CODE_UNTRUSTED) +HDRS_APP=$(HDRS_ELF64) $(HDRS_PTS) $(HDRS_LOADER) $(HDRS_UNTRUSTED) + +## ———————————————————————— Enclave code and headers ———————————————————————— ## +CODE_ENCLAVE=$(CODE_RUNTIME) $(CODE_TRUSTED) $(CODE_CAPAS) +HDRS_ENCLAVE=$(HDRS_RUNTIME) $(HDRS_TRUSTED) + +## ———————————————————————————————— Includes ———————————————————————————————— ## +COMMON_INCLUDES = -Iinclude -I$(CAPA_LIB)/include -I$(COMMON_LIB)/include -I$(DLL_LIB)/include -I$(SDK)/include +APP_INCLUDES = $(COMMON_INCLUDES) -I$(ELF64)/include -I$(PTS)/include -I$(DRIVER)/include + +ifeq ($(KVM), 1) + APP_INCLUDES+=-I$(CONTALLOC)/include +endif + +ifeq ($(ARCH), riscv) + APP_INCLUDES+=-pthread +endif + +## ————————————————————— Configuration for the install —————————————————————— ## +ifeq ($(ARCH), riscv) +DISK_PATH ?= /tmp/ubuntu_riscv_mount/tyche/programs +endif + +TYCHOOLS_PATH ?= ../../../../../crates/tychools/ + +## ———————————————————————————————— Targets ————————————————————————————————— ## + +app: $(CODE_APP) $(HDRS_APP) + $(GCC) -DTYCHE_USER_SPACE=1 $(LOADER_BACKEND) -g $(APP_INCLUDES) -o $@ $(CODE_APP) + + +ifeq ($(ARCH), riscv) + +enclave: $(CODE_ENCLAVE) $(HDRS_ENCLAVE) + echo "riscv" + echo $(GCC) + $(GCC) -DTYCHE_USER_SPACE=2 -DTYCHE_ENCLAVE=1 -DCONFIG_RISCV=1 -g $(COMMON_INCLUDES) -nostdlib -static -o $@ $(CODE_ENCLAVE) -Wl,--section-start=.data=0x16000 + +rot_iso: app enclave + cargo -C $(TYCHOOLS_PATH) install --path . --locked + tychools instrument -s manifests/rot_iso.json --riscv-enabled + chmod +x rot_iso + rm app enclave + +rot_enclave: app enclave + cargo -Z unstable-options -C $(TYCHOOLS_PATH) install --path . --locked + tychools instrument -s manifests/default.json --riscv-enabled + chmod +x rot_enclave + rm app enclave + +attestation_enclave: app enclave + echo "Building attestation enclave for RISCV with TPM RoT" + cargo -Z unstable-options -C $(TYCHOOLS_PATH) install --path . --locked + tychools instrument -s manifests/default.json --riscv-enabled + chmod +x rot_enclave + tychools instrument -s manifests/rot_iso.json --riscv-enabled + chmod +x rot_iso + rm app enclave +endif + +install_disk: all + mkdir -p $(DISK_PATH) + cp -t $(DISK_PATH) rot_enclave + cp -t $(DISK_PATH) rot_iso + +.PHONY: clean + +clean: + rm rot_enclave + rm rot_iso diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/README.md b/C/libraries/sdktyche/example/enclave_rot_riscv/README.md new file mode 100644 index 000000000..cfdf72aa9 --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/README.md @@ -0,0 +1,63 @@ +# Simple Enclave Example + + +## How to run + +This application runs by default or if you type: + +``` +./rot_enclave +``` + +### What it does + +The application loads the enclave and performs numerous calls to it, in order to fetch the entire attestation from Tyche. It then queries Tychools to verify the attestation. + +### Sample output +In the case the platform is equipped with a TPM: +``` +[LOG @../../..//sdktyche/loader/lib.c:269 parse_domain] Parsed tychools binary +INFO | tyche::attestation_domain] Finished calculating the hash! +[LOG @untrusted/main.c:167 main] The binary enclave has been loaded! +[LOG @untrusted/main.c:176 main] Calling the enclave, good luck! +[LOG @untrusted/main.c:112 hello_world] Executing HELLO_WORLD enclave + +[LOG @untrusted/main.c:117 hello_world] Nonce sent by the client is 2ff07b60 +[LOG @untrusted/main.c:92 main] The binary enclave has been loaded! +[LOG @untrusted/main.c:97 read_tychools_response] Answer from tychools + +[LOG @untrusted/main.c:101 read_tychools_response] Message was verified + +[LOG @untrusted/main.c:101 read_tychools_response] TPM PCR redigest is verified + +[LOG @untrusted/main.c:101 read_tychools_response] TPM signature is verified +[LOG @untrusted/main.c:70 hello_world] All done! + +[LOG @untrusted/main.c:106 main] Done, have a good day! +``` + +In the case a platform is without a TPM: + +``` +dev@tyche:/tyche/programs$ ./rot_enclave +[LOG @../../..//sdktyche/loader/lib.c:269 parse_domain] Parsed tychools binary +INFO | tyche::attestation_domain] Finished calculating the hash! +[LOG @untrusted/main.c:167 main] The binary enclave has been loaded! +[LOG @untrusted/main.c:176 main] Calling the enclave, good luck! +[LOG @untrusted/main.c:112 hello_world] Executing HELLO_WORLD enclave + +[LOG @untrusted/main.c:117 hello_world] Nonce sent by the client is 2ff07b60 +[LOG @untrusted/main.c:92 main] The binary enclave has been loaded! +[LOG @untrusted/main.c:97 read_tychools_response] Answer from tychools + +[LOG @untrusted/main.c:101 read_tychools_response] Message was verified + +[LOG @untrusted/main.c:101 read_tychools_response] TPM PCR redigest was not verified + +[LOG @untrusted/main.c:101 read_tychools_response] TPM signature is verified +[LOG @untrusted/main.c:70 hello_world] All done! + +[LOG @untrusted/main.c:106 main] Done, have a good day! +``` + +Note the signature verification still goes through and is validated. The contents of the PCR however, are not. diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/include/enclave_app.h b/C/libraries/sdktyche/example/enclave_rot_riscv/include/enclave_app.h new file mode 100644 index 000000000..cc7159692 --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/include/enclave_app.h @@ -0,0 +1,34 @@ +#ifndef __INCLUDE_ENCLAVE_APP_H__ +#define __INCLUDE_ENCLAVE_APP_H__ + +/// Configuration for the enclave. +/// This allows to select which example to run via shared memory. +typedef struct { + /// arguments for this application. + void* args; +} config_t; + +typedef unsigned long long nonce_t; +typedef unsigned long long phys_offset_t; +#define PUB_KEY_SIZE 32 +#define SIGNED_DATA_SIZE 64 +#define TPM_ATTESTATION_SIZE 129 +#define TPM_SIGNATURE_SIZE 384 +#define TPM_MODULUS_SIZE 384 +#define SUPPOSED_ATTESTATION_SIZE 993 +#define CALC_REPORT 0 +#define READ_REPORT 1 +/// Hello world argument. +typedef struct { + char reply[30]; + unsigned long long report_size; + nonce_t nonce; + char pub_key[PUB_KEY_SIZE]; + char signed_enclave_data[SIGNED_DATA_SIZE]; + char tpm_signature[TPM_SIGNATURE_SIZE]; + char tpm_modulus[TPM_MODULUS_SIZE]; + char tpm_attestation[TPM_ATTESTATION_SIZE]; +} __attribute__((__packed__)) hello_world_t; + + +#endif diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/manifests/default.json b/C/libraries/sdktyche/example/enclave_rot_riscv/manifests/default.json new file mode 100644 index 000000000..b3ca9567f --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/manifests/default.json @@ -0,0 +1,28 @@ +{ + "untrusted_bin": { + "path": "app" + }, + "kern_bin": { + "path":"enclave", + "ops":[ + { + "AddSegment":{ + "size":8192, + "tpe":"KernelStackConf", + "write":true,"exec":false + } + }, + { + "AddSegment":{ + "start": 3145728, + "size":8192, + "tpe":"KernelShared", + "write":true, + "exec":false + } + } + ] + }, + "generate_pts": true, + "output": "rot_enclave" +} diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/manifests/rot_iso.json b/C/libraries/sdktyche/example/enclave_rot_riscv/manifests/rot_iso.json new file mode 100644 index 000000000..1347a592c --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/manifests/rot_iso.json @@ -0,0 +1,26 @@ +{ + "kern_bin": { + "path":"enclave", + "ops":[ + { + "AddSegment":{ + "size":8192, + "tpe":"KernelStackConf", + "write":true,"exec":false + } + }, + { + "AddSegment":{ + "start": 3145728, + "size":8192, + "tpe":"KernelShared", + "write":true, + "exec":false + } + } + ] + }, + "generate_pts": true, + "output": "rot_iso" + } + diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/rot_iso b/C/libraries/sdktyche/example/enclave_rot_riscv/rot_iso new file mode 100755 index 000000000..972835157 Binary files /dev/null and b/C/libraries/sdktyche/example/enclave_rot_riscv/rot_iso differ diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/trusted/main.c b/C/libraries/sdktyche/example/enclave_rot_riscv/trusted/main.c new file mode 100644 index 000000000..cc4e1aacd --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/trusted/main.c @@ -0,0 +1,148 @@ +#include "sdk_tyche_rt.h" +#include "common.h" +#include "tyche_api.h" +#include "enclave_app.h" +// ———————————————————————————————— Globals ————————————————————————————————— // +config_t* shared = NULL; +// ————————————————————————— Static define —————————————————————————— // +static int tyche_domain_attestation(usize nonce, unsigned long long* ans, int mode) { + vmcall_frame_t frame = { + .vmcall = 20, + .arg_1 = nonce, + .arg_2 = mode, + }; + if (tyche_call(&frame) != SUCCESS) { + goto failure; + } + + ans[0] = frame.value_1; + ans[1] = frame.value_2; + ans[2] = frame.value_3; + ans[3] = frame.value_4; + ans[4] = frame.value_5; + ans[5] = frame.value_6; + + return SUCCESS; +failure: + return FAILURE; + +} + +static int tyche_domain_attestation_size(unsigned long long* val){ + vmcall_frame_t frame = { + .vmcall = 23, + }; + if (tyche_call(&frame) != SUCCESS) { + goto failure; + } + + *val = frame.value_1; + + return SUCCESS; +failure: + return FAILURE; +} + + +// ————————————————————————— HELLO_WORLD Functions —————————————————————————— // +// + +const char* message = "Hello World!\n\t\0"; +const char* message2 = "Bye Bye! :)!\n\t\0"; +const char* message3 = "Done attestation!\n\t\0"; + +void put_bytes_in_arr(char* arr, unsigned long long val) { + for(int i = 0; i < 8;i++) { + char c = (char)(val & 0xFF); + *arr = c; + arr++; + val>>=8; + } +} + +static void tyche_attestation_size(hello_world_t* ans) { + unsigned long long val; + tyche_domain_attestation_size(&val); + ans->report_size = val; + //Sanity check on the size of the attestation + if(val!=SUPPOSED_ATTESTATION_SIZE){ + val = 0; + } +} + +void tyche_call_wrapper(usize nonce, hello_world_t* ans, int mode) { + unsigned long long vals[6]; + tyche_domain_attestation(nonce, vals, mode); + //Sanity check on the size of the attestation + if(!(ans->report_size)){ + return; + } + //Sanity check on whether we already are out of bound + if (6*8*mode>(993)){ + return; + } + //Check whether we can fill 48 bytes worth of stuff or not + if (6*8*(mode+1)>(993)){ + put_bytes_in_arr(((char *) &(ans->tpm_attestation))+96, vals[0]); + put_bytes_in_arr(((char *) &(ans->tpm_attestation))+104, vals[1]); + put_bytes_in_arr(((char *) &(ans->tpm_attestation))+112, vals[2]); + put_bytes_in_arr(((char *) &(ans->tpm_attestation))+120, vals[3]); + *(((char *) &(ans->tpm_attestation))+128) = (char) (vals[4] & 0x0FF); + } + char* start_address = ((char*) &(ans->pub_key)) + 6*8*mode; + for(int i=0; i<6; i++){ + put_bytes_in_arr(start_address, vals[i]); + start_address +=8; + } +} + +void my_memcpy(void* dest, void* src, int size) +{ + char* ptr_dest = (char*) dest; + char* ptr_src = (char*) src; + for (int i = 0; i < size; i++) { + ptr_dest[i] = ptr_src[i]; + } + ptr_dest[size] = '\0'; +} + +void print_message(void* input, int size) +{ + hello_world_t* msg = (hello_world_t*) (&(shared->args)); + if (msg == 0) { + int* ptr = (int*) 0xdeadbeef; + *ptr = 0xdeadbabe; + } + my_memcpy(msg->reply, input, size); +} + +void hello_world(void) +{ + hello_world_t* msg = (hello_world_t*) (&(shared->args)); + print_message((void*) message, 15); + + // Do a return. + gate_call(); + nonce_t nonce = msg->nonce; + + //The current implementation passes data from/to the application through registers. + //Ideally, the report is passed through shared memory and would require only one call to Tyche. + + + //Sample call to retrieve the size of the attestation in case it's unknown. + tyche_attestation_size(msg); + //For our use case, 22 calls to Tyche to retrieve the entire enclave report + for(int i=0; i<22;i++){ + tyche_call_wrapper(nonce, msg, i); + } + + print_message((void*)message3, 20); +} + +// ————————————————————————————— Entry Function ————————————————————————————— // + +void trusted_entry(void) +{ + shared = (config_t*) get_default_shared_buffer(); + hello_world(); +} diff --git a/C/libraries/sdktyche/example/enclave_rot_riscv/untrusted/main.c b/C/libraries/sdktyche/example/enclave_rot_riscv/untrusted/main.c new file mode 100644 index 000000000..815ee023f --- /dev/null +++ b/C/libraries/sdktyche/example/enclave_rot_riscv/untrusted/main.c @@ -0,0 +1,186 @@ +#define _GNU_SOURCE +#include "common.h" +#include "common_log.h" +#include "enclave_app.h" +#include "sdk_tyche.h" +#include "sdk_tyche_rt.h" +#include +#include +#include +#include +#include +#include +#include + +// ———————————————————————————— Local Variables ————————————————————————————— // + +usize has_faulted = FAILURE; + +tyche_domain_t* enclave = NULL; + +config_t* shared = NULL; + +FILE* file_tychools; +FILE* tychools_response; + +// ———————————————————————————————— Helpers ————————————————————————————————— // + +/// Looks up for the shared memory region with the enclave. +static void* find_default_shared(tyche_domain_t* enclave) +{ + domain_shared_memory_t* shared_sec = NULL; + if (enclave == NULL) { + ERROR("Supplied enclave is null."); + goto failure; + } + // Find the shared region. + dll_foreach(&(enclave->shared_regions), shared_sec, list) { + if (shared_sec->segment->p_type == KERNEL_SHARED) { + return (void*)(shared_sec->untrusted_vaddr); + } + } + ERROR("Unable to find the shared buffer for the enclave!"); +failure: + return NULL; +} + +// ————————————————————————— Application functions —————————————————————————— // + +void call_tychools(nonce_t nonce, unsigned long long offset) { + char cmd[256]; + sprintf(cmd, "sudo chmod ugo+rx tychools;./tychools attestation --att-src=file_tychools.txt --src-bin=rot_iso --offset=0x%llx --nonce=0x%x --riscv-enabled", offset, nonce); + LOG("cmd %s", cmd); + system(cmd); +} + +void write_to_tychools(hello_world_t* msg) { + file_tychools = fopen("file_tychools.txt", "w"); + if(file_tychools == NULL) { + LOG("File failed to open tychools file\n"); + } + else { + LOG("Writing public key and data to tychools file\n"); + for(int i = 0;i < 32;i++) { + uint32_t x = (uint32_t)msg->pub_key[i] & 0x0FF; + fprintf(file_tychools, "%u\n", x); + } + for(int i = 0;i < 64;i++) { + uint32_t x = (uint32_t)msg->signed_enclave_data[i] & 0x0FF; + fprintf(file_tychools, "%u\n", x); + } + LOG("\n"); + for(int i = 0;i < 384;i++) { + uint32_t x = (uint32_t)msg->tpm_signature[i] & 0x0FF; + fprintf(file_tychools, "%u\n", x); + } + + for(int i = 0;i < 384;i++) { + uint32_t x = (uint32_t)msg->tpm_modulus[i] & 0x0FF; + fprintf(file_tychools, "%u\n", x); + } + + for(int i = 0;i < 129;i++) { + uint32_t x = (uint32_t)msg->tpm_attestation[i] & 0x0FF; + fprintf(file_tychools, "%u\n", x); + } + + fclose(file_tychools); + } +} + +void read_tychools_response() { + tychools_response = fopen("tychools_response.txt", "r"); + if(tychools_response == NULL) { + LOG("Failed to open a reponse file"); + } + else { + LOG("Answer from tychools\n"); + char* line = NULL; + int len = 0; + while ((getline(&line, &len, tychools_response)) != -1) { + LOG("%s", line); + } + fclose(tychools_response); + } +} + +/// Calls the enclave twice to print a message. +int hello_world() +{ + TEST(enclave != NULL); + TEST(shared != NULL); + LOG("Executing HELLO_WORLD enclave\n"); + hello_world_t* msg = (hello_world_t*)(&(shared->args)); + // Generating random nonce + const nonce_t mod = (1e9 + 7); + nonce_t nonce = rand() % mod; + LOG("Nonce sent by the client is %llx", nonce); + msg->nonce = nonce; + + // Call the enclave. + if (sdk_call_domain(enclave) != SUCCESS) { + ERROR("Unable to call the enclave %d!", enclave->handle); + goto failure; + } + LOG("First enclave message:\n%s", msg->reply); + + // Call to enclave, which will do attestation + LOG("Calling enclave to execute attestation"); + if (sdk_call_domain(enclave) != SUCCESS) { + ERROR("Unable to call the enclave a second time %lld!", enclave->handle); + goto failure; + } + LOG("Second enclave message: \n%s", msg->reply); + write_to_tychools(msg); + LOG("Calling the command to tychools to compare the result\n"); + //TODO: copy fix from simple-enclave + call_tychools(msg->nonce, /*enclave->map.physoffset*/ 0); + read_tychools_response(); + + // Clean up. + if (sdk_delete_domain(enclave) != SUCCESS) { + ERROR("Unable to delete the enclave %lld", enclave->handle); + goto failure; + } + LOG("All done!"); + return SUCCESS; +failure: + return FAILURE; +} + + +// —————————————————————————————————— Main —————————————————————————————————— // +int main(int argc, char *argv[]) { + // Allocate the enclave. + enclave = malloc(sizeof(tyche_domain_t)); + if (enclave == NULL) { + ERROR("Unable to allocate enclave structure"); + goto failure; + } + // Init the enclave. + if (sdk_create_domain( + enclave, argv[0], + DEFAULT_CORES, ALL_TRAPS, DEFAULT_PERM) != SUCCESS) { + ERROR("Unable to parse the enclave"); + goto failure; + } + LOG("The binary enclave has been loaded!"); + + // Find the shared region. + shared = (config_t*) find_default_shared(enclave); + if (shared == NULL) { + ERROR("Unable to find the default shared region."); + goto failure; + } + + LOG("Calling the enclave, good luck!"); + + if (hello_world() != SUCCESS) { + ERROR("Oups... we received a failure... good luck debugging."); + goto failure; + } + LOG("Done, have a good day!"); + return SUCCESS; +failure: + return FAILURE; +} diff --git a/Cargo.lock b/Cargo.lock index 288fcff07..0e6270bb6 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -191,9 +191,9 @@ dependencies = [ [[package]] name = "cc" -version = "1.0.79" +version = "1.0.90" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50d30906286121d95be3d479533b458f87493b30a4b5f79a607db8f5d11aa91f" +checksum = "8cd6604a82acf3039f1144f54b8eb34e91ffba622051189e71b781822d5ee1f5" [[package]] name = "cfg-if" @@ -386,6 +386,17 @@ dependencies = [ "typenum", ] +[[package]] +name = "getrandom" +version = "0.2.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "190092ea657667030ac6a35e305e62fc4dd69fd98ac98631e5d3a2b1575a12b5" +dependencies = [ + "cfg-if", + "libc", + "wasi", +] + [[package]] name = "goblin" version = "0.6.1" @@ -433,6 +444,12 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fed44880c466736ef9a5c5b5facefb5ed0785676d0c02d612db14e54f0d84286" +[[package]] +name = "hex" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f24254aa9a54b5c858eaee2f5bccdb46aaf0e486a595ed5fd8f86ba55232a70" + [[package]] name = "indexmap" version = "1.9.3" @@ -512,9 +529,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.146" +version = "0.2.153" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" +checksum = "9c198f91728a82281a64e1f4f9eeb25d82cb32a5de251c6bd1b5154d63a8e7bd" [[package]] name = "libtyche" @@ -565,7 +582,7 @@ version = "0.1.0" dependencies = [ "log", "qemu", - "spin 0.9.4", + "spin 0.9.8", ] [[package]] @@ -781,6 +798,21 @@ dependencies = [ "bitflags", ] +[[package]] +name = "ring" +version = "0.17.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c17fa4cb658e3583423e915b9f3acc01cceaee1860e33d59ebae66adc3a2dc0d" +dependencies = [ + "cc", + "cfg-if", + "getrandom", + "libc", + "spin 0.9.8", + "untrusted", + "windows-sys 0.52.0", +] + [[package]] name = "riscv_csrs" version = "0.1.0" @@ -800,7 +832,7 @@ dependencies = [ "log", "riscv_csrs", "riscv_utils", - "spin 0.9.4", + "spin 0.9.8", ] [[package]] @@ -883,7 +915,7 @@ dependencies = [ "logger", "mmu", "qemu", - "spin 0.9.4", + "spin 0.9.8", "stage_two_abi", "vga", "vmx", @@ -991,9 +1023,9 @@ checksum = "6e63cff320ae2c57904679ba7cb63280a3dc4613885beafb148ee7bf9aa9042d" [[package]] name = "spin" -version = "0.9.4" +version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7f6002a767bff9e83f8eeecf883ecb8011875a21ae8da43bffb817a57e78cc09" +checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" dependencies = [ "lock_api", ] @@ -1115,7 +1147,7 @@ dependencies = [ "riscv_sbi", "riscv_tyche", "riscv_utils", - "spin 0.9.4", + "spin 0.9.8", "stage_two_abi", "utils", "vga", @@ -1135,6 +1167,7 @@ dependencies = [ "elf", "elfloader", "goblin", + "hex", "ioctl-sys", "libc", "log", @@ -1142,10 +1175,12 @@ dependencies = [ "nix", "num", "object", + "ring", "serde", "serde_json", "sha2", "simple_logger", + "untrusted", "utils", "xmas-elf", ] @@ -1173,6 +1208,12 @@ version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c4f5b37a154999a8f3f98cc23a628d850e154479cd94decf3414696e12e31aaf" +[[package]] +name = "untrusted" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" + [[package]] name = "utf8parse" version = "0.2.1" @@ -1237,6 +1278,12 @@ dependencies = [ "libc", ] +[[package]] +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + [[package]] name = "winapi" version = "0.3.9" @@ -1265,13 +1312,13 @@ version = "0.42.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7" dependencies = [ - "windows_aarch64_gnullvm", - "windows_aarch64_msvc", - "windows_i686_gnu", - "windows_i686_msvc", - "windows_x86_64_gnu", - "windows_x86_64_gnullvm", - "windows_x86_64_msvc", + "windows_aarch64_gnullvm 0.42.2", + "windows_aarch64_msvc 0.42.2", + "windows_i686_gnu 0.42.2", + "windows_i686_msvc 0.42.2", + "windows_x86_64_gnu 0.42.2", + "windows_x86_64_gnullvm 0.42.2", + "windows_x86_64_msvc 0.42.2", ] [[package]] @@ -1280,7 +1327,16 @@ version = "0.45.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "75283be5efb2831d37ea142365f009c02ec203cd29a3ebecbc093d52315b66d0" dependencies = [ - "windows-targets", + "windows-targets 0.42.2", +] + +[[package]] +name = "windows-sys" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" +dependencies = [ + "windows-targets 0.52.4", ] [[package]] @@ -1289,13 +1345,28 @@ version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8e5180c00cd44c9b1c88adb3693291f1cd93605ded80c250a75d472756b4d071" dependencies = [ - "windows_aarch64_gnullvm", - "windows_aarch64_msvc", - "windows_i686_gnu", - "windows_i686_msvc", - "windows_x86_64_gnu", - "windows_x86_64_gnullvm", - "windows_x86_64_msvc", + "windows_aarch64_gnullvm 0.42.2", + "windows_aarch64_msvc 0.42.2", + "windows_i686_gnu 0.42.2", + "windows_i686_msvc 0.42.2", + "windows_x86_64_gnu 0.42.2", + "windows_x86_64_gnullvm 0.42.2", + "windows_x86_64_msvc 0.42.2", +] + +[[package]] +name = "windows-targets" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7dd37b7e5ab9018759f893a1952c9420d060016fc19a472b4bb20d1bdd694d1b" +dependencies = [ + "windows_aarch64_gnullvm 0.52.4", + "windows_aarch64_msvc 0.52.4", + "windows_i686_gnu 0.52.4", + "windows_i686_msvc 0.52.4", + "windows_x86_64_gnu 0.52.4", + "windows_x86_64_gnullvm 0.52.4", + "windows_x86_64_msvc 0.52.4", ] [[package]] @@ -1304,42 +1375,84 @@ version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "597a5118570b68bc08d8d59125332c54f1ba9d9adeedeef5b99b02ba2b0698f8" +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bcf46cf4c365c6f2d1cc93ce535f2c8b244591df96ceee75d8e83deb70a9cac9" + [[package]] name = "windows_aarch64_msvc" version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e08e8864a60f06ef0d0ff4ba04124db8b0fb3be5776a5cd47641e942e58c4d43" +[[package]] +name = "windows_aarch64_msvc" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da9f259dd3bcf6990b55bffd094c4f7235817ba4ceebde8e6d11cd0c5633b675" + [[package]] name = "windows_i686_gnu" version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c61d927d8da41da96a81f029489353e68739737d3beca43145c8afec9a31a84f" +[[package]] +name = "windows_i686_gnu" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b474d8268f99e0995f25b9f095bc7434632601028cf86590aea5c8a5cb7801d3" + [[package]] name = "windows_i686_msvc" version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "44d840b6ec649f480a41c8d80f9c65108b92d89345dd94027bfe06ac444d1060" +[[package]] +name = "windows_i686_msvc" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1515e9a29e5bed743cb4415a9ecf5dfca648ce85ee42e15873c3cd8610ff8e02" + [[package]] name = "windows_x86_64_gnu" version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8de912b8b8feb55c064867cf047dda097f92d51efad5b491dfb98f6bbb70cb36" +[[package]] +name = "windows_x86_64_gnu" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5eee091590e89cc02ad514ffe3ead9eb6b660aedca2183455434b93546371a03" + [[package]] name = "windows_x86_64_gnullvm" version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "26d41b46a36d453748aedef1486d5c7a85db22e56aff34643984ea85514e94a3" +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77ca79f2451b49fa9e2af39f0747fe999fcda4f5e241b2898624dca97a1f2177" + [[package]] name = "windows_x86_64_msvc" version = "0.42.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9aec5da331524158c6d1a4ac0ab1541149c0b9505fde06423b02f5ef0106b9f0" +[[package]] +name = "windows_x86_64_msvc" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32b752e52a2da0ddfbdbcc6fceadfeede4c939ed16d13e648833a61dfb611ed8" + [[package]] name = "x2apic" version = "0.1.0" diff --git a/crates/attestation/src/signature.rs b/crates/attestation/src/signature.rs index 1fdc66af3..1ee0c61f0 100644 --- a/crates/attestation/src/signature.rs +++ b/crates/attestation/src/signature.rs @@ -9,7 +9,38 @@ pub type AttestationSignature = Signature; pub const MAX_ATTESTATION_DATA_SZ: usize = 8; pub const ATTESTATION_DATA_SZ: usize = MAX_ATTESTATION_DATA_SZ + 32; -#[derive(Copy, Clone)] +//TPM-added size constants +pub const TPM_ATTESTATION_SZ: usize = 129; +pub const TPM_SIG_SZ: usize = 384; +pub const TPM_MODULUS_SZ: usize = 384; +pub const ATTESTATION_TOTAL_SZ: usize = + ATTESTATION_DATA_SZ + TPM_ATTESTATION_SZ + TPM_SIG_SZ + TPM_MODULUS_SZ; + +//TPM-added types +pub type TpmSignature = [u8; TPM_SIG_SZ]; +pub type TpmModulus = [u8; TPM_MODULUS_SZ]; +pub type TpmAttestation = [u8; TPM_ATTESTATION_SZ]; + +//TPM hardcoded signature stuff + +pub static mut TPM_ATTESTATION: TpmAttestation = [0; TPM_ATTESTATION_SZ]; + +pub static mut TPM_SIGNATURE: TpmSignature = [0; TPM_SIG_SZ]; + +pub static mut TPM_MODULUS: TpmModulus = [0; TPM_MODULUS_SZ]; + +#[cfg(target_arch = "riscv64")] +#[derive(Copy, Clone, Debug)] +pub struct EnclaveReport { + pub public_key: PublicKey, //32 bytes + pub signed_enclave_data: AttestationSignature, //64 bytes + pub tpm_signature: TpmSignature, //384 + pub tpm_modulus: TpmModulus, //384 + pub tpm_attestation: TpmAttestation, //129 +} + +#[cfg(target_arch = "x86_64")] +#[derive(Copy, Clone, Debug)] pub struct EnclaveReport { pub public_key: PublicKey, pub signed_enclave_data: AttestationSignature, diff --git a/crates/riscv_tyche/src/lib.rs b/crates/riscv_tyche/src/lib.rs index 24e114006..f6ebd22d7 100644 --- a/crates/riscv_tyche/src/lib.rs +++ b/crates/riscv_tyche/src/lib.rs @@ -16,4 +16,7 @@ pub struct RVManifest { pub next_mode: usize, pub coldboot_hartid: usize, pub num_harts: usize, + pub modulus: [u8; 384], + pub signature: [u8; 384], + pub attestation: [u8; 129], } diff --git a/crates/tychools/Cargo.toml b/crates/tychools/Cargo.toml index 59b45f2e0..4cc89c511 100644 --- a/crates/tychools/Cargo.toml +++ b/crates/tychools/Cargo.toml @@ -27,5 +27,8 @@ sha2 = "0.6.0" clap-num = "1.0.2" ed25519-compact = { path = "../../vendor/forked_signature" } attest_client = { path = "../attest_client" } +ring = "0.17.8" +hex = "0.4.3" +untrusted = "0.9.0" [features] diff --git a/crates/tychools/src/attestation.rs b/crates/tychools/src/attestation.rs index 5453ae181..d77de9c9d 100644 --- a/crates/tychools/src/attestation.rs +++ b/crates/tychools/src/attestation.rs @@ -2,9 +2,11 @@ use std::fs::read_to_string; use std::path::PathBuf; use ed25519_compact::{PublicKey, Signature}; +use hex::encode; use object::elf::{PF_R, PF_W, PF_X}; use object::read::elf::ProgramHeader; -use sha2::{Digest, Sha256}; +use ring; +use sha2::{Digest, Sha256, Sha384}; use crate::elf_modifier::TychePF::PfH; use crate::elf_modifier::{ModifiedELF, ModifiedSegment, TychePhdrTypes, DENDIAN}; @@ -73,6 +75,45 @@ fn hash_segments_info(enclave: &Box, hasher: &mut Sha256, offset: u } } +fn construct_der_rsa_pkey(modulus: &[u8]) -> Vec { + let mut der_payload: Vec = std::vec::Vec::new(); + let mut add_0: u8 = 0; + if modulus[0] > 127 { + add_0 = add_0 + 1; + } + // DER shenanigans + //// Sequence tag + der_payload.push(0x30); + //// Long form length encoding + der_payload.push(0x82); + //// Length bytes (394) + der_payload.extend([1, (137 + add_0)]); + //// Modulus object + //// Integer tag + der_payload.push(0x02); + //// Long form length encoding + der_payload.push(0x82); + //// Length of 384 bytes (+1 0x0 sometimes) + der_payload.extend([1, 128 + add_0]); + //// Modulus data + //Context-specific byte : if first byte of modulus is >128, add 0x0 byte in front to make it + //positive. + if add_0 > 0 { + der_payload.push(0x0); + } + + der_payload.extend(modulus); + //// public exponent object + der_payload.push(0x02); + + // Short form length + der_payload.push(0x03); + // 65537 + der_payload.extend([1, 0, 1]); + + der_payload +} + pub fn attest(src: &PathBuf, offset: u64, riscv_enabled: bool) -> (u128, u128) { let data = std::fs::read(src).expect("Unable to read source file"); let mut hasher = Sha256::default(); @@ -92,6 +133,15 @@ pub fn attest(src: &PathBuf, offset: u64, riscv_enabled: bool) -> (u128, u128) { const MSG_SZ: usize = 32 + 8; const PB_KEY_SZ: usize = 32; const ENC_DATA_SZ: usize = 64; + +const TPM_SIG_SZ: usize = 384; +const TPM_ATT_SZ: usize = 129; + +const PB_KEY_SZ_1: usize = 31; +const ENC_DATA_SZ_1: usize = 63; +const TPM_SIG_SZ_1: usize = 383; + +const TPM_PCR_REDIGEST: &str = "2152d35c16e4f59d3d95e09299c2c73218aec31164d32a000f6e2bc6a0e785fb5c31271dc7fea029e5a9dbebc571129f"; use std::fs::File; use std::io::Write; @@ -117,21 +167,106 @@ pub fn attestation_check( log::trace!("Nonce {:#x}", nonce); let mut pub_key_arr: [u8; PB_KEY_SZ] = [0; PB_KEY_SZ]; let mut enc_data_arr: [u8; ENC_DATA_SZ] = [0; ENC_DATA_SZ]; + let mut tpm_sig_arr: [u8; TPM_SIG_SZ] = [0; TPM_SIG_SZ]; + let mut tpm_mod_arr: [u8; TPM_SIG_SZ] = [0; TPM_SIG_SZ]; + let mut tpm_att_arr: [u8; TPM_ATT_SZ] = [0; TPM_ATT_SZ]; + let mut tpm_sig_verified: bool = false; + let mut tpm_pcr_verified: bool = false; let mut index_pub = 0; let mut index_enc = 0; + let mut index_sig = 0; + let mut index_mod = 0; + let mut index_att = 0; let mut cnt = 0; //read lines from file and make public key and encrypted data for line in read_to_string(src_att).unwrap().lines() { let num: u32 = line.parse().unwrap(); - if cnt < PB_KEY_SZ { - pub_key_arr[index_pub] = num as u8; - index_pub += 1; + + //RISC-V parsing of enclave report (we have DRoT w/ OpenSBI) + if riscv_enabled { + match cnt { + ..=PB_KEY_SZ_1 if index_enc == 0 => { + pub_key_arr[index_pub] = num as u8; + index_pub += 1; + } + ..=ENC_DATA_SZ_1 if index_sig == 0 => { + cnt = if index_enc == 0 { cnt - PB_KEY_SZ } else { cnt }; + enc_data_arr[index_enc] = num as u8; + index_enc += 1; + } + ..=TPM_SIG_SZ_1 if index_mod == 0 => { + cnt = if index_sig == 0 { + cnt - ENC_DATA_SZ + } else { + cnt + }; + tpm_sig_arr[index_sig] = num as u8; + index_sig += 1; + } + ..=TPM_SIG_SZ if index_att == 0 => { + cnt = if index_mod == 0 { + cnt - TPM_SIG_SZ + } else { + cnt + }; + if cnt != TPM_SIG_SZ { + tpm_mod_arr[index_mod] = num as u8; + index_mod += 1; + } else { + tpm_att_arr[0] = num as u8; + } + } + _ if index_att < TPM_ATT_SZ - 1 => { + tpm_att_arr[index_att + 1] = num as u8; + index_att += 1; + } + _ => {} + } + //x86 parsing (we don't have TPM support) } else { - enc_data_arr[index_enc] = num as u8; - index_enc += 1; + if cnt < PB_KEY_SZ { + pub_key_arr[index_pub] = num as u8; + index_pub += 1; + } else { + enc_data_arr[index_enc] = num as u8; + index_enc += 1; + } } cnt += 1; } + + if riscv_enabled { + log::info!("TPM_PCR_REDIGEST IS : {}", TPM_PCR_REDIGEST); + log::info!("TPM_PCR_REDIGEST IS : {:?}", encode(&tpm_att_arr[81..])); + if encode(&(tpm_att_arr[81..])) == TPM_PCR_REDIGEST { + tpm_pcr_verified = true; + } else { + tpm_pcr_verified = false; + } + + let der_payload = construct_der_rsa_pkey(&tpm_mod_arr); + + let tpm_rsa_pkey = ring::signature::UnparsedPublicKey::new( + &ring::signature::RSA_PKCS1_3072_8192_SHA384, + der_payload, + ); + + if let Ok(_t) = tpm_rsa_pkey.verify(&tpm_att_arr, &tpm_sig_arr) { + tpm_sig_verified = true; + } else { + tpm_sig_verified = false; + } + let mut tpm_hasher = Sha384::new(); + tpm_hasher.input(&tpm_att_arr); + let rehash: [u8; 48] = tpm_hasher + .result() + .as_slice() + .try_into() + .expect("Ain't working that way"); + log::info!("Computed attestation rehash is:"); + log::info!("{}", encode(&rehash)); + } + let pkey: PublicKey = PublicKey::new(pub_key_arr); let sig: Signature = Signature::new(enc_data_arr); @@ -144,14 +279,40 @@ pub fn attestation_check( copy_arr(&mut message, &u64::to_le_bytes(nonce), 32); { let mut data_file = File::create("tychools_response.txt").expect("creation failed"); + if let Ok(_r) = pkey.verify(message, &sig) { log::info!("Verified!"); data_file.write(b"Message verified").expect("Write failed"); } else { log::info!("Not verified!"); data_file - .write(b"Message was not verified") + .write(b"Message was not verified\n") .expect("Write failed"); } + if riscv_enabled { + if tpm_pcr_verified { + log::info!("TPM PCR redigest is verified!"); + data_file + .write(b"TPM PCR redigest is verified\n") + .expect("Write failed"); + } else { + log::info!("TPM PCR redigest was not verified!"); + data_file + .write(b"TPM PCR redigest was not verified\n") + .expect("Write failed"); + } + + if tpm_sig_verified { + log::info!("TPM signature is verified!"); + data_file + .write(b"TPM signature is verified") + .expect("Write failed"); + } else { + log::info!("TPM signature was not verified!\n"); + data_file + .write(b"TPM signature was not verified\n") + .expect("Write failed"); + } + } } } diff --git a/justfile b/justfile index 53ba81bcd..497b60437 100644 --- a/justfile +++ b/justfile @@ -24,11 +24,12 @@ default_dbg := "/tmp/dbg-" + env_var('USER') default_smp := "1" extra_arg := "" -qemu-riscv := "../qemu/build/riscv64-softmmu/qemu-system-riscv64" +qemu-riscv := "../qemu-riscv/build/riscv64-softmmu/qemu-system-riscv64" drive-riscv := "ubuntu-22.04.3-preinstalled-server-riscv64+unmatched.img" kernel-riscv := "builds/linux-riscv/arch/riscv/boot/Image" bios-riscv := "opensbi-stage1/build/platform/generic/firmware/fw_payload.bin" dev-riscv := "-device virtio-rng-pci" +tpm-dev := "-device tpm-tis-device,tpmdev=tpm0 -tpmdev emulator,id=tpm0,chardev=tpm-chardev -chardev socket,id=tpm-chardev,path=/tmp/tpm-dev-" + env_var('USER')+ "/sock" bios-riscv-gdb := "opensbi-stage1/build/platform/generic/firmware/fw_payload.elf" riscv-linux-dir := "builds/linux-riscv" riscv-vmlinux := "builds/linux-riscv/vmlinux" @@ -263,8 +264,20 @@ _tpm: swtpm socket --tpm2 --tpmstate dir={{tpm_path}} --ctrl type=unixio,path={{tpm_path}}/sock & fi +_tpm_riscv: + #!/usr/bin/env sh + if pgrep -u $USER swtpm; + then + echo "TPM is running" + else + echo "Starting TPM" + mkdir -p {{tpm_path}}/ + swtpm socket --tpm2 --tpmstate dir={{tpm_path}} --ctrl type=unixio,path={{tpm_path}}/sock --locality allow-set-locality & + fi + run_riscv: - {{qemu-riscv}} -nographic -drive "file={{drive-riscv}},format=raw,if=virtio" -cpu rv64,h=true -M virt -m 4G -bios {{bios-riscv}} -kernel {{kernel-riscv}} -append "root=/dev/vda1 rw console=ttyS0 earlycon=sbi quiet" -smp 1 {{dev-riscv}} + @just _tpm_riscv + {{qemu-riscv}} -nographic -drive "file={{drive-riscv}},format=raw,if=virtio" -cpu rv64,h=true -M virt -m 4G -bios {{bios-riscv}} -kernel {{kernel-riscv}} -append "root=/dev/vda1 rw console=ttyS0 earlycon=sbi quiet" -smp 1 {{dev-riscv}} {{tpm-dev}} run_riscv_gdb: {{qemu-riscv}} -nographic -drive "file={{drive-riscv}},format=raw,if=virtio" -cpu rv64,h=true -M virt -m 4G -bios {{bios-riscv}} -kernel {{kernel-riscv}} -append "root=/dev/vda1 rw console=ttyS0 earlycon=sbi quiet" -smp 1 {{dev-riscv}} -gdb tcp::1234 -S diff --git a/linux b/linux index 7085131e6..334f8ec7d 160000 --- a/linux +++ b/linux @@ -1 +1 @@ -Subproject commit 7085131e65ea9231126536aac74f308d082304c3 +Subproject commit 334f8ec7d3672353402ccdf6f45dd0dc96fd6238 diff --git a/monitor/tyche/src/attestation_domain.rs b/monitor/tyche/src/attestation_domain.rs index 5b93b1e4d..e3bdbfb6c 100644 --- a/monitor/tyche/src/attestation_domain.rs +++ b/monitor/tyche/src/attestation_domain.rs @@ -1,5 +1,9 @@ +#![allow(unused_imports)] use attestation::hashing::{self, TycheHasher}; -use attestation::signature::{self, get_attestation_keys, EnclaveReport, ATTESTATION_DATA_SZ}; +use attestation::signature::{ + self, get_attestation_keys, EnclaveReport, ATTESTATION_DATA_SZ, TPM_ATTESTATION, TPM_MODULUS, + TPM_SIGNATURE, +}; use capa_engine::{CapaEngine, CapaInfo, Domain, Handle, MemOps, NextCapaToken}; use spin::MutexGuard; @@ -68,7 +72,8 @@ pub fn calculate_attestation_hash(engine: &mut MutexGuard<'_, CapaEngine>, domai hash_capa_info(&mut hasher, engine, domain); - log::trace!("Finished calculating the hash!"); + log::info!("Finished calculating the hash!"); + engine.set_hash(domain, hashing::get_hash(&mut hasher)); } @@ -82,6 +87,37 @@ fn copy_array(dst: &mut [u8], src: &[u8], index: usize) { } } +#[cfg(target_arch = "riscv64")] +pub fn attest_domain( + engine: &mut MutexGuard, + current: Handle, + nonce: usize, + mode: usize, +) -> Option { + if mode == 0 { + let enc_hash = engine[current].get_hash(); + let mut sign_data: [u8; ATTESTATION_DATA_SZ] = [0; ATTESTATION_DATA_SZ]; + enc_hash.to_byte_arr(&mut sign_data, 0); + copy_array(&mut sign_data, &usize::to_le_bytes(nonce), 32); + let (pb_key, priv_key) = get_attestation_keys(); + let signed_enc_data = signature::sign_attestation_data(&sign_data, priv_key); + unsafe { + let rep = EnclaveReport { + public_key: pb_key, + signed_enclave_data: signed_enc_data, + tpm_signature: TPM_SIGNATURE, + tpm_modulus: TPM_MODULUS, + tpm_attestation: TPM_ATTESTATION, + }; + engine.set_report(current, rep); + Some(rep) + } + } else { + engine[current].get_report() + } +} + +#[cfg(target_arch = "x86_64")] pub fn attest_domain( engine: &mut MutexGuard, current: Handle, diff --git a/monitor/tyche/src/calls.rs b/monitor/tyche/src/calls.rs index fdb66d8da..355a3d200 100644 --- a/monitor/tyche/src/calls.rs +++ b/monitor/tyche/src/calls.rs @@ -28,3 +28,7 @@ pub const REVOKE_ALIASED_REGION: usize = 21; pub const SERIALIZE_ATTESTATION: usize = 22; /// For benchmarks to measure the cost of communication with tyche. pub const TEST_CALL: usize = 30; +#[cfg(target_arch = "riscv64")] +/// This call is only used by the Dynamic Root of Trust example. +/// As such, it is not exposed by the Tyche driver API. +pub const ENCLAVE_ATTESTATION_SIZE: usize = 23; diff --git a/monitor/tyche/src/rcframe.rs b/monitor/tyche/src/rcframe.rs index a3da2fb0d..0777a1a4f 100644 --- a/monitor/tyche/src/rcframe.rs +++ b/monitor/tyche/src/rcframe.rs @@ -48,10 +48,12 @@ pub fn drop_rc(pool: &mut RCFramePool, v: Handle) { if count == 0 { let frame = pool[v].frame; pool.free(v); - unsafe { - allocator() - .free_frame(frame.phys_addr) - .expect("Error freeing frame"); + if frame.phys_addr.as_u64() != 0 { + unsafe { + allocator() + .free_frame(frame.phys_addr) + .expect("Error freeing frame"); + } } } } diff --git a/monitor/tyche/src/riscv/guest.rs b/monitor/tyche/src/riscv/guest.rs index 7311f3ec3..a8894ba93 100644 --- a/monitor/tyche/src/riscv/guest.rs +++ b/monitor/tyche/src/riscv/guest.rs @@ -1,6 +1,7 @@ use core::arch::asm; use core::sync::atomic::AtomicUsize; +use attestation::signature::ATTESTATION_TOTAL_SZ; use capa_engine::{Bitmaps, Domain, Handle, LocalCapa, NextCapaToken}; use riscv_csrs::*; use riscv_pmp::clear_pmp; @@ -17,6 +18,7 @@ use super::monitor; use crate::arch::cpuid; use crate::calls; use crate::riscv::monitor::apply_core_updates; +use crate::riscv::riscv_tpm_attestation::pass_attestation; const EMPTY_ACTIVE_DOMAIN: Mutex>> = Mutex::new(None); static ACTIVE_DOMAIN: [Mutex>>; NUM_HARTS] = [EMPTY_ACTIVE_DOMAIN; NUM_HARTS]; @@ -277,6 +279,8 @@ pub fn misaligned_load_handler(reg_state: &mut RegisterState) { let hartid = cpuid(); active_dom = get_active_dom(hartid).unwrap(); + log::debug!("Tyche call with code : {:x}", tyche_call); + match tyche_call { calls::CREATE_DOMAIN => { log::debug!("Create Domain"); @@ -466,69 +470,227 @@ pub fn misaligned_load_handler(reg_state: &mut RegisterState) { todo!("Implement that one only if needed."); } calls::ENCLAVE_ATTESTATION => { - log::trace!("Get attestation!"); + log::info!("Get attestation!"); if let Some(report) = monitor::do_domain_attestation(active_dom, arg_1, arg_2) { - reg_state.a0 = 0; - if arg_2 == 0 { - reg_state.a1 = usize::from_le_bytes( - report.public_key.as_slice()[0..8].try_into().unwrap(), - ) as isize; - reg_state.a2 = usize::from_le_bytes( - report.public_key.as_slice()[8..16].try_into().unwrap(), - ); - reg_state.a3 = usize::from_le_bytes( - report.public_key.as_slice()[16..24].try_into().unwrap(), - ) as usize; - reg_state.a4 = usize::from_le_bytes( - report.public_key.as_slice()[24..32].try_into().unwrap(), - ) as usize; - reg_state.a5 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[0..8] - .try_into() - .unwrap(), - ) as usize; - reg_state.a6 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[8..16] - .try_into() - .unwrap(), - ) as usize; - } else if arg_2 == 1 { - reg_state.a1 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[16..24] - .try_into() - .unwrap(), - ) as isize; - reg_state.a2 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[24..32] - .try_into() - .unwrap(), - ); - reg_state.a3 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[32..40] - .try_into() - .unwrap(), - ); - reg_state.a4 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[40..48] - .try_into() - .unwrap(), - ); - reg_state.a5 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[48..56] - .try_into() - .unwrap(), - ); - reg_state.a6 = usize::from_le_bytes( - report.signed_enclave_data.as_slice()[56..64] - .try_into() - .unwrap(), - ); - } - } else { - log::trace!("Attestation error"); - reg_state.a0 = 1; + let regs: (isize, isize, [usize; 5]) = pass_attestation(&report, arg_2); + reg_state.a0 = regs.0; + reg_state.a1 = regs.1; + reg_state.a2 = regs.2[0]; + reg_state.a3 = regs.2[1]; + reg_state.a4 = regs.2[2]; + reg_state.a5 = regs.2[3]; + reg_state.a6 = regs.2[4]; + + // match arg_2{ + // 0 => { + // reg_state.a1 = isize::from_le_bytes( + // report.public_key.as_slice()[0..8].try_into().unwrap(), + // ); + // reg_state.a2 = usize::from_le_bytes( + // report.public_key.as_slice()[8..16].try_into().unwrap(), + // ); + // reg_state.a3 = usize::from_le_bytes( + // report.public_key.as_slice()[16..24].try_into().unwrap(), + // ) as usize; + // reg_state.a4 = usize::from_le_bytes( + // report.public_key.as_slice()[24..32].try_into().unwrap(), + // ) as usize; + // reg_state.a5 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[0..8] + // .try_into() + // .unwrap(), + // ) as usize; + // reg_state.a6 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[8..16] + // .try_into() + // .unwrap(), + // ) as usize; + // }, + // 1 => { + // reg_state.a1 = isize::from_le_bytes( + // report.signed_enclave_data.as_slice()[16..24] + // .try_into() + // .unwrap(), + // ); + // reg_state.a2 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[24..32] + // .try_into() + // .unwrap(), + // ); + // reg_state.a3 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[32..40] + // .try_into() + // .unwrap(), + // ); + // reg_state.a4 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[40..48] + // .try_into() + // .unwrap(), + // ); + // reg_state.a5 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[48..56] + // .try_into() + // .unwrap(), + // ); + // reg_state.a6 = usize::from_le_bytes( + // report.signed_enclave_data.as_slice()[56..64] + // .try_into() + // .unwrap(), + // ); + // }, + // 2..=9 => { + // let mut offset : usize = (arg_2-2)*6*8; + // let mut upper_bound: usize = offset+8; + // reg_state.a1 = isize::from_le_bytes( + // report.tpm_signature.as_slice()[offset..upper_bound] + // .try_into() + // .unwrap(), + // ); + // offset += 8; + // reg_state.a2 = usize::from_le_bytes( + // report.tpm_signature.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset += 8; + // reg_state.a3 = usize::from_le_bytes( + // report.tpm_signature.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a4 = usize::from_le_bytes( + // report.tpm_signature.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a5 = usize::from_le_bytes( + // report.tpm_signature.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a6 = usize::from_le_bytes( + // report.tpm_signature.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // }, + // 10..=17 => { + // let mut offset : usize = (arg_2-10)*6*8; + // reg_state.a1 = isize::from_le_bytes( + // report.tpm_modulus.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset += 8; + // reg_state.a2 = usize::from_le_bytes( + // report.tpm_modulus.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset += 8; + // reg_state.a3 = usize::from_le_bytes( + // report.tpm_modulus.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a4 = usize::from_le_bytes( + // report.tpm_modulus.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a5 = usize::from_le_bytes( + // report.tpm_modulus.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a6 = usize::from_le_bytes( + // report.tpm_modulus.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // }, + // 18 | 19 => { + // let mut offset : usize = (arg_2-18)*6*8; + // reg_state.a1 = isize::from_le_bytes( + // report.tpm_attestation.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset += 8; + // reg_state.a2 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset += 8; + // reg_state.a3 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a4 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a5 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // offset+=8; + // reg_state.a6 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[offset..offset+8] + // .try_into() + // .unwrap(), + // ); + // }, + // 20 => { + // reg_state.a1 = isize::from_le_bytes( + // report.tpm_attestation.as_slice()[96..104] + // .try_into() + // .unwrap(), + // ); + // reg_state.a2 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[104..112] + // .try_into() + // .unwrap(), + // ); + // reg_state.a3 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[112..120] + // .try_into() + // .unwrap(), + // ); + // reg_state.a4 = usize::from_le_bytes( + // report.tpm_attestation.as_slice()[120..128] + // .try_into() + // .unwrap(), + // ); + // reg_state.a5 = + // usize::from(report.tpm_attestation[128]); + // }, + // _ => { + // log::trace!("Attestation error"); + // reg_state.a0 = 1; + // }, + // } } } + calls::ENCLAVE_ATTESTATION_SIZE => { + log::trace!("Request for attestation size!"); + //We consider we can request the size no matter whether the report exists yet or + //not. + reg_state.a0 = 0x0; + reg_state.a1 = ATTESTATION_TOTAL_SZ as isize; + } _ => { /*TODO: Invalid Tyche Call*/ log::debug!("Invalid Tyche Call: {:x}", reg_state.a0); diff --git a/monitor/tyche/src/riscv/init.rs b/monitor/tyche/src/riscv/init.rs index bbc11ce8c..9aba00b0d 100644 --- a/monitor/tyche/src/riscv/init.rs +++ b/monitor/tyche/src/riscv/init.rs @@ -1,6 +1,7 @@ use core::arch::asm; use core::sync::atomic::Ordering; +use attestation::signature::{TPM_ATTESTATION, TPM_MODULUS, TPM_SIGNATURE}; use capa_engine::{Domain, Handle}; use riscv_tyche::RVManifest; use riscv_utils::{ @@ -21,13 +22,22 @@ pub fn arch_entry_point(hartid: usize, manifest: RVManifest, log_level: log::Lev hartid ); log::info!( - "Manifest Content: {:x} {:x} {:x} {:x} {:x}", + "Manifest Content: {:x} {:x} {:x} {:x} {:x}, {:?}\n {:?}\n, {:?}", manifest.coldboot_hartid, manifest.next_arg1, manifest.next_addr, manifest.next_mode, - manifest.num_harts + manifest.num_harts, + manifest.modulus, + manifest.signature, + manifest.attestation ); + unsafe { + TPM_MODULUS = manifest.modulus; + TPM_SIGNATURE = manifest.signature; + TPM_ATTESTATION = manifest.attestation; + } + let mhartid = cpuid(); log::debug!("==========Coldboot MHARTID: {} ===========", mhartid); diff --git a/monitor/tyche/src/riscv/mod.rs b/monitor/tyche/src/riscv/mod.rs index f004e096c..e00ee66a6 100644 --- a/monitor/tyche/src/riscv/mod.rs +++ b/monitor/tyche/src/riscv/mod.rs @@ -9,6 +9,7 @@ mod filtered_fields; pub mod guest; mod init; mod monitor; +mod riscv_tpm_attestation; use core::arch::asm; pub use init::arch_entry_point; diff --git a/monitor/tyche/src/riscv/riscv_tpm_attestation.rs b/monitor/tyche/src/riscv/riscv_tpm_attestation.rs new file mode 100644 index 000000000..65542eb04 --- /dev/null +++ b/monitor/tyche/src/riscv/riscv_tpm_attestation.rs @@ -0,0 +1,215 @@ +use attestation::signature::EnclaveReport; + +pub fn pass_attestation(report: &EnclaveReport, call_nb: usize) -> (isize, isize, [usize; 5]) { + let mut arr: [usize; 5] = [0; 5]; + let mut val0: isize = 0; + let mut val1: isize = 0; + let mut val2: usize = 0; + let mut val3: usize = 0; + let mut val4: usize = 0; + let mut val5: usize = 0; + let mut val6: usize = 0; + + match call_nb { + 0 => { + val1 = isize::from_le_bytes(report.public_key.as_slice()[0..8].try_into().unwrap()); + val2 = usize::from_le_bytes(report.public_key.as_slice()[8..16].try_into().unwrap()); + val3 = usize::from_le_bytes(report.public_key.as_slice()[16..24].try_into().unwrap()) + as usize; + val4 = usize::from_le_bytes(report.public_key.as_slice()[24..32].try_into().unwrap()) + as usize; + val5 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[0..8] + .try_into() + .unwrap(), + ) as usize; + val6 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[8..16] + .try_into() + .unwrap(), + ) as usize; + } + 1 => { + val1 = isize::from_le_bytes( + report.signed_enclave_data.as_slice()[16..24] + .try_into() + .unwrap(), + ); + val2 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[24..32] + .try_into() + .unwrap(), + ); + val3 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[32..40] + .try_into() + .unwrap(), + ); + val4 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[40..48] + .try_into() + .unwrap(), + ); + val5 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[48..56] + .try_into() + .unwrap(), + ); + val6 = usize::from_le_bytes( + report.signed_enclave_data.as_slice()[56..64] + .try_into() + .unwrap(), + ); + } + 2..=9 => { + let mut offset: usize = (call_nb - 2) * 6 * 8; + let mut upper_bound: usize = offset + 8; + val1 = isize::from_le_bytes( + report.tpm_signature.as_slice()[offset..upper_bound] + .try_into() + .unwrap(), + ); + offset += 8; + val2 = usize::from_le_bytes( + report.tpm_signature.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val3 = usize::from_le_bytes( + report.tpm_signature.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val4 = usize::from_le_bytes( + report.tpm_signature.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val5 = usize::from_le_bytes( + report.tpm_signature.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val6 = usize::from_le_bytes( + report.tpm_signature.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + } + 10..=17 => { + let mut offset: usize = (call_nb - 10) * 6 * 8; + val1 = isize::from_le_bytes( + report.tpm_modulus.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val2 = usize::from_le_bytes( + report.tpm_modulus.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val3 = usize::from_le_bytes( + report.tpm_modulus.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val4 = usize::from_le_bytes( + report.tpm_modulus.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val5 = usize::from_le_bytes( + report.tpm_modulus.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val6 = usize::from_le_bytes( + report.tpm_modulus.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + } + 18 | 19 => { + let mut offset: usize = (call_nb - 18) * 6 * 8; + val1 = isize::from_le_bytes( + report.tpm_attestation.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val2 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val3 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val4 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val5 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + offset += 8; + val6 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[offset..offset + 8] + .try_into() + .unwrap(), + ); + } + 20 => { + val1 = isize::from_le_bytes( + report.tpm_attestation.as_slice()[96..104] + .try_into() + .unwrap(), + ); + val2 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[104..112] + .try_into() + .unwrap(), + ); + val3 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[112..120] + .try_into() + .unwrap(), + ); + val4 = usize::from_le_bytes( + report.tpm_attestation.as_slice()[120..128] + .try_into() + .unwrap(), + ); + val5 = usize::from(report.tpm_attestation[128]); + } + _ => { + log::trace!("Attestation error"); + val0 = 1; + } + }; + if val0 == 0 { + arr[0] = val2; + arr[1] = val3; + arr[2] = val4; + arr[3] = val5; + arr[4] = val6; + } + (val0, val1, arr) +} diff --git a/monitor/tyche/src/x86_64/monitor.rs b/monitor/tyche/src/x86_64/monitor.rs index d6c0efacc..ba1799bf9 100644 --- a/monitor/tyche/src/x86_64/monitor.rs +++ b/monitor/tyche/src/x86_64/monitor.rs @@ -31,7 +31,7 @@ use super::vmx_helper::{dump_host_state, load_host_state}; use super::{cpuid, vmx_helper}; use crate::allocator::{allocator, PAGE_SIZE}; use crate::attestation_domain::{attest_domain, calculate_attestation_hash}; -use crate::rcframe::{RCFrame, RCFramePool, EMPTY_RCFRAME}; +use crate::rcframe::{drop_rc, RCFrame, RCFramePool, EMPTY_RCFRAME}; use crate::sync::Barrier; // ————————————————————————— Statics & Backend Data ————————————————————————— // @@ -423,6 +423,7 @@ pub fn do_init_child_context( .allocate_frame() .expect("Unable to allocate frame"); let rc = RCFrame::new(frame); + drop_rc(&mut *rcvmcs, dest.vmcs); dest.vmcs = rcvmcs.allocate(rc).expect("Unable to allocate rc frame"); //Init the frame, it needs the identifier. vmx_state.vmxon.init_frame(frame);