Modify the protect-integrity tool to print result on file

This commit is contained in:
LI Qing 2021-06-04 13:52:14 +08:00 committed by Zongmin.Gu
parent d098e65d67
commit 1e24dcea6a
6 changed files with 92 additions and 47 deletions

@ -45,23 +45,15 @@ pub fn load_config(config_path: &str, expected_mac: &sgx_aes_gcm_128bit_tag_t) -
} }
// This value will be modified during occlum build // This value will be modified during occlum build
#[no_mangle] #[used]
#[link_section = ".builtin_config"] #[link_section = ".builtin_config"]
static OCCLUM_JSON_MAC: [i8; 48] = [0; 48]; static OCCLUM_JSON_MAC: [u8; 47] = [0; 47];
fn conf_get_hardcoded_file_mac() -> sgx_aes_gcm_128bit_tag_t { fn conf_get_hardcoded_file_mac() -> sgx_aes_gcm_128bit_tag_t {
assert!( // Use black_box to avoid the compiler's optimization for OCCLUM_JSON_MAC
*OCCLUM_JSON_MAC.last().unwrap() == 0, let json_mac = std::hint::black_box(&OCCLUM_JSON_MAC);
"must be a null-terminated C string" let mac_str = String::from_utf8(json_mac.to_vec()).expect("MAC contains non UTF-8 characters");
); let mac = parse_mac(&mac_str).expect("MAC string cannot be converted to numbers");
let mac_str = unsafe {
CStr::from_ptr(&OCCLUM_JSON_MAC as *const i8)
.to_str()
.expect("MAC contains non UTF-8 characters")
};
let mac = parse_mac(mac_str).expect("MAC string cannot be converted to numbers");
mac mac
} }

@ -18,6 +18,8 @@
#![feature(slice_ptr_get)] #![feature(slice_ptr_get)]
#![feature(maybe_uninit_extra)] #![feature(maybe_uninit_extra)]
#![feature(get_mut_unchecked)] #![feature(get_mut_unchecked)]
// for std::hint::black_box
#![feature(test)]
#[macro_use] #[macro_use]
extern crate alloc; extern crate alloc;

@ -8,6 +8,7 @@ INITFS := $(instance_dir)/initfs
INITFS_IMAGE := $(instance_dir)/build/initfs/__ROOT/metadata INITFS_IMAGE := $(instance_dir)/build/initfs/__ROOT/metadata
INITFS_IMAGE_MAC := $(instance_dir)/build/initfs/.ROOT_MAC INITFS_IMAGE_MAC := $(instance_dir)/build/initfs/.ROOT_MAC
JSON_CONF := $(instance_dir)/Occlum.json JSON_CONF := $(instance_dir)/Occlum.json
CONF_TMP_MAC := $(instance_dir)/build/tmp_mac
LIBOS := $(instance_dir)/build/lib/$(libos_lib).$(occlum_version) LIBOS := $(instance_dir)/build/lib/$(libos_lib).$(occlum_version)
SIGNED_ENCLAVE := $(instance_dir)/build/lib/libocclum-libos.signed.so SIGNED_ENCLAVE := $(instance_dir)/build/lib/libocclum-libos.signed.so
@ -33,14 +34,9 @@ endif
SHELL:=/bin/bash SHELL:=/bin/bash
define get_occlum_sys_conf_file_mac define get_occlum_file_mac
LD_LIBRARY_PATH="$(SGX_SDK)/sdk_libs" \ LD_LIBRARY_PATH="$(SGX_SDK)/sdk_libs" \
"$(occlum_dir)/build/bin/occlum-protect-integrity" show-mac "$(instance_dir)/build/.Occlum_sys.json.protected" "$(occlum_dir)/build/bin/occlum-protect-integrity" show-mac $(1) $(2)
endef
define get_occlum_user_conf_file_mac
LD_LIBRARY_PATH="$(SGX_SDK)/sdk_libs" \
"$(occlum_dir)/build/bin/occlum-protect-integrity" show-mac "$(instance_dir)/build/Occlum.json.protected"
endef endef
.PHONY : all clean .PHONY : all clean
@ -60,13 +56,13 @@ $(SIGNED_ENCLAVE): $(LIBOS)
$(LIBOS): $(instance_dir)/build/.Occlum_sys.json.protected $(LIBOS): $(instance_dir)/build/.Occlum_sys.json.protected
@echo "Building libOS..." @echo "Building libOS..."
@export OCCLUM_BUILTIN_SYS_CONF_FILE_MAC=`$(get_occlum_sys_conf_file_mac)` ; \ @cd $(instance_dir)/build/lib && \
cd $(instance_dir)/build/lib && \ cp "$(occlum_dir)/build/lib/$(libos_lib).$(occlum_version)" . && \
cp "$(occlum_dir)/build/lib/$(libos_lib).$(occlum_version)" . && ln -sf "$(libos_lib).$(occlum_version)" "libocclum-libos.so.$(major_ver)" && \ ln -sf "$(libos_lib).$(occlum_version)" "libocclum-libos.so.$(major_ver)" && \
ln -sf "libocclum-libos.so.$(major_ver)" libocclum-libos.so ; \ ln -sf "libocclum-libos.so.$(major_ver)" libocclum-libos.so ; \
echo -e "$$OCCLUM_BUILTIN_SYS_CONF_FILE_MAC\c" > temp_mac_file && \ $(call get_occlum_file_mac, "$(instance_dir)/build/.Occlum_sys.json.protected", "$(CONF_TMP_MAC)") && \
objcopy --update-section .builtin_config=temp_mac_file libocclum-libos.so && \ objcopy --update-section .builtin_config="$(CONF_TMP_MAC)" libocclum-libos.so && \
rm temp_mac_file rm -f "$(CONF_TMP_MAC)"
$(instance_dir)/build/.Occlum_sys.json.protected: $(instance_dir)/build/.Occlum_sys.json $(instance_dir)/build/.Occlum_sys.json.protected: $(instance_dir)/build/.Occlum_sys.json
@cd "$(instance_dir)/build" ; \ @cd "$(instance_dir)/build" ; \
@ -108,13 +104,13 @@ $(INITFS_IMAGE): $(INITFS) $(INITFS_DIRS) $(INITFS_FILES) $(IMAGE_CONFIG_JSON) $
"$(INITFS_IMAGE_MAC)" "$(INITFS_IMAGE_MAC)"
$(IMAGE_CONFIG_JSON): $(instance_dir)/build/Occlum.json.protected $(IMAGE_CONFIG_JSON): $(instance_dir)/build/Occlum.json.protected
@export OCCLUM_CONF_FILE_MAC=`$(get_occlum_user_conf_file_mac)` ; \ @$(call get_occlum_file_mac, "$(instance_dir)/build/Occlum.json.protected", "$(CONF_TMP_MAC)") && \
echo "EXPORT => OCCLUM_CONF_FILE_MAC = $$OCCLUM_CONF_FILE_MAC" ; \
[ -n "$(SECURE_IMAGE_KEY)" ] && \ [ -n "$(SECURE_IMAGE_KEY)" ] && \
jq -n --arg mac_val "$$OCCLUM_CONF_FILE_MAC" \ jq -n --arg mac_val "`cat $(CONF_TMP_MAC)`" \
'{image_type: "encrypted", occlum_json_mac: $$mac_val}' > $(IMAGE_CONFIG_JSON) || \ '{image_type: "encrypted", occlum_json_mac: $$mac_val}' > $(IMAGE_CONFIG_JSON) || \
jq -n --arg mac_val "$$OCCLUM_CONF_FILE_MAC" \ jq -n --arg mac_val "`cat $(CONF_TMP_MAC)`" \
'{image_type: "integrity-only", occlum_json_mac: $$mac_val}' > $(IMAGE_CONFIG_JSON) '{image_type: "integrity-only", occlum_json_mac: $$mac_val}' > $(IMAGE_CONFIG_JSON)
@rm -f "$(CONF_TMP_MAC)"
$(instance_dir)/build/Occlum.json.protected: $(instance_dir)/build/Occlum.json $(instance_dir)/build/Occlum.json.protected: $(instance_dir)/build/Occlum.json
@cd "$(instance_dir)/build" ; \ @cd "$(instance_dir)/build" ; \

@ -218,19 +218,31 @@ static int initialize_enclave(void) {
return 0; return 0;
} }
// File stream for output buffer
static FILE *fp_output = NULL;
// ========================================================================== // ==========================================================================
// OCalls // OCalls
// ========================================================================== // ==========================================================================
void ocall_print(const char *str) { void ocall_print(const char *str) {
printf("%s", str); if (fp_output) {
fprintf(fp_output, "%s", str);
} else {
fprintf(stdout, "%s", str);
}
} }
void ocall_eprint(const char *str) { void ocall_eprint(const char *str) {
fprintf(stderr, "%s", str); fprintf(stderr, "%s", str);
} }
int ocall_open(const char *path) { int ocall_open_for_write(const char *path) {
return open(path, O_WRONLY | O_CREAT | O_TRUNC, 00644);
}
int ocall_open_for_read(const char *path) {
return open(path, O_RDONLY); return open(path, O_RDONLY);
} }
@ -256,8 +268,8 @@ static void print_help(void) {
"\n" "\n"
"Usage:\n" "Usage:\n"
"\tprotect-integrity protect <ordinary_file>\n" "\tprotect-integrity protect <ordinary_file>\n"
"\tprotect-integrity show <protected_file>\n" "\tprotect-integrity show <protected_file> [<output_file>]\n"
"\tprotect-integrity show-mac <protected_file>\n"); "\tprotect-integrity show-mac <protected_file> [<output_file>]\n");
} }
#define CMD_ERROR (-1) #define CMD_ERROR (-1)
@ -271,15 +283,23 @@ static int parse_args(
char *argv[], char *argv[],
/* outputs */ /* outputs */
int *arg_command, int *arg_command,
char **arg_file_path) { char **arg_file_path,
if (argc != 3) { return -1; } char **arg_output_path) {
if (argc < 3 || argc > 4) { return -1; }
if (strcmp(argv[1], "protect") == 0) { if (strcmp(argv[1], "protect") == 0) {
if (argc != 3) { return -1; }
*arg_command = CMD_PROTECT; *arg_command = CMD_PROTECT;
} else if (strcmp(argv[1], "show") == 0) { } else if (strcmp(argv[1], "show") == 0) {
*arg_command = CMD_SHOW; *arg_command = CMD_SHOW;
if (argc == 4) {
*arg_output_path = argv[3];
}
} else if (strcmp(argv[1], "show-mac") == 0) { } else if (strcmp(argv[1], "show-mac") == 0) {
*arg_command = CMD_SHOW_MAC; *arg_command = CMD_SHOW_MAC;
if (argc == 4) {
*arg_output_path = argv[3];
}
} else { } else {
return -1; return -1;
} }
@ -296,7 +316,8 @@ int SGX_CDECL main(int argc, char *argv[]) {
/* Parse arguments */ /* Parse arguments */
int arg_command = CMD_ERROR; int arg_command = CMD_ERROR;
char *arg_file_path = NULL; char *arg_file_path = NULL;
if (parse_args(argc, argv, &arg_command, &arg_file_path) < 0) { char *arg_output_path = NULL;
if (parse_args(argc, argv, &arg_command, &arg_file_path, &arg_output_path) < 0) {
print_help(); print_help();
return -1; return -1;
} }
@ -328,7 +349,8 @@ int SGX_CDECL main(int argc, char *argv[]) {
} }
case CMD_SHOW: { case CMD_SHOW: {
const char *input_path = arg_file_path; const char *input_path = arg_file_path;
if (ecall_show(global_eid, &ret, input_path)) { const char *output_path = arg_output_path;
if (ecall_show(global_eid, &ret, input_path, output_path)) {
fprintf(stderr, "Error: ecall failed\n"); fprintf(stderr, "Error: ecall failed\n");
ret = -1; ret = -1;
} }
@ -336,10 +358,22 @@ int SGX_CDECL main(int argc, char *argv[]) {
} }
case CMD_SHOW_MAC: { case CMD_SHOW_MAC: {
const char *input_path = arg_file_path; const char *input_path = arg_file_path;
const char *output_path = arg_output_path;
if (output_path) {
fp_output = fopen(output_path, "w");
if (!fp_output) {
fprintf(stderr, "Error: failed to open %s for output \n", output_path);
ret = -1;
break;
}
}
if (ecall_show_mac(global_eid, &ret, input_path)) { if (ecall_show_mac(global_eid, &ret, input_path)) {
fprintf(stderr, "Error: ecall failed\n"); fprintf(stderr, "Error: ecall failed\n");
ret = -1; ret = -1;
} }
if (fp_output) {
fclose(fp_output);
}
break; break;
} }
default: { default: {

@ -8,13 +8,15 @@ enclave {
trusted { trusted {
public int ecall_protect([in, string] const char* input_path, public int ecall_protect([in, string] const char* input_path,
[in, string] const char* ouput_path); [in, string] const char* ouput_path);
public int ecall_show([in, string] const char* input_path); public int ecall_show([in, string] const char* input_path,
[in, string] const char* output_path);
public int ecall_show_mac([in, string] const char* input_path); public int ecall_show_mac([in, string] const char* input_path);
}; };
untrusted { untrusted {
// File operations // File operations
int ocall_open([in, string] const char* path); int ocall_open_for_write([in, string] const char* path);
int ocall_open_for_read([in, string] const char* path);
ssize_t ocall_read(int fd, [out, size=size] void* buf, size_t size); ssize_t ocall_read(int fd, [out, size=size] void* buf, size_t size);
ssize_t ocall_write(int fd, [in, size=size] const void* buf, size_t size); ssize_t ocall_write(int fd, [in, size=size] const void* buf, size_t size);
int ocall_close(int fd); int ocall_close(int fd);

@ -39,10 +39,15 @@ static void print_mac(sgx_aes_gcm_128bit_tag_t *mac) {
printf("\n"); printf("\n");
} }
static int open_for_write(const char *path) {
static int open(const char *path) {
int fd = 0; int fd = 0;
ocall_open(&fd, path); ocall_open_for_write(&fd, path);
return fd;
}
static int open_for_read(const char *path) {
int fd = 0;
ocall_open_for_read(&fd, path);
return fd; return fd;
} }
@ -74,7 +79,7 @@ int ecall_protect(const char *input_path, const char *output_path) {
size_t len; size_t len;
char buf[4 * 1024]; char buf[4 * 1024];
input_file = open(input_path); input_file = open_for_read(input_path);
if (input_file < 0) { if (input_file < 0) {
eprintf("Error: cannot open the input file at %s\n", input_path); eprintf("Error: cannot open the input file at %s\n", input_path);
goto on_error; goto on_error;
@ -107,9 +112,10 @@ on_error:
return -1; return -1;
} }
int ecall_show(const char *protected_file_path) { int ecall_show(const char *protected_file_path, const char *show_path) {
SGX_FILE *protected_file = NULL; SGX_FILE *protected_file = NULL;
ssize_t len; ssize_t len;
int output_fd = 1; /* stdout */
char buf[4 * 1024]; char buf[4 * 1024];
protected_file = sgx_fopen_integrity_only(protected_file_path, "r"); protected_file = sgx_fopen_integrity_only(protected_file_path, "r");
@ -117,9 +123,16 @@ int ecall_show(const char *protected_file_path) {
eprintf("Error: failed to open the given protected file %s\n", protected_file_path); eprintf("Error: failed to open the given protected file %s\n", protected_file_path);
goto on_error; goto on_error;
} }
if (show_path) {
output_fd = open_for_write(show_path);
if (output_fd < 0) {
eprintf("Error: failed to open the given show_path %s\n", show_path);
goto on_error;
}
}
while ((len = sgx_fread(buf, 1, sizeof(buf), protected_file)) > 0) { while ((len = sgx_fread(buf, 1, sizeof(buf), protected_file)) > 0) {
write(1/* stdout */, buf, len); write(output_fd, buf, len);
} }
if (sgx_ferror(protected_file)) { if (sgx_ferror(protected_file)) {
@ -128,11 +141,17 @@ int ecall_show(const char *protected_file_path) {
} }
sgx_fclose(protected_file); sgx_fclose(protected_file);
if (output_fd > 1) {
close(output_fd);
}
return 0; return 0;
on_error: on_error:
if (protected_file != NULL) { if (protected_file != NULL) {
sgx_fclose(protected_file); sgx_fclose(protected_file);
} }
if (output_fd > 1) {
close(output_fd);
}
return -1; return -1;
} }