April 8, 2021 at 11:46 am
Analysis Artifact SGX

class protected_fs_file
    union {
        struct {
            uint64_t meta_data_node_number; // for recovery purpose, so it is easy to write this node
            meta_data_node_t file_meta_data; // actual data from disk's meta data node
        recovery_node_t meta_data_recovery_node;

    meta_data_encrypted_t encrypted_part_plain; // encrypted part of meta data node, decrypted
    file_mht_node_t root_mht; // the root of the mht is always needed (for files bigger than 3KB)

    FILE* file; // OS's FILE pointer
    open_mode_t open_mode;
    uint8_t read_only;
    int64_t offset; // current file position (user's view)
    bool end_of_file; // flag

    int64_t real_file_size;
    bool need_writing; // flag
    uint32_t last_error; // last operation error
    protected_fs_status_e file_status;
    sgx_thread_mutex_t mutex;

    uint8_t use_user_kdk_key;
    sgx_aes_gcm_128bit_key_t user_kdk_key; // recieved from user, used instead of the seal key

    sgx_aes_gcm_128bit_key_t cur_key;
    sgx_aes_gcm_128bit_key_t session_master_key;
    uint32_t master_key_count;
    char recovery_filename[RECOVERY_FILE_MAX_LEN]; // might include full path to the file

    lru_cache cache;

    // these don't change after init...
    sgx_iv_t empty_iv;
    sgx_report_t report;

    void init_fields();
    bool cleanup_filename(const char* src, char* dest);
    bool parse_mode(const char* mode);
    bool file_recovery(const char* filename);
    bool init_existing_file(const char* filename, const char* clean_filename, const sgx_aes_gcm_128bit_key_t* import_key);
    bool init_new_file(const char* clean_filename);
    bool generate_secure_blob(sgx_aes_gcm_128bit_key_t* key, const char* label, uint64_t physical_node_number, sgx_aes_gcm_128bit_tag_t* output);
    bool generate_secure_blob_from_user_kdk(bool restore);
    bool init_session_master_key();
    bool derive_random_node_key(uint64_t physical_node_number);
    bool generate_random_meta_data_key();
    bool restore_current_meta_data_key(const sgx_aes_gcm_128bit_key_t* import_key);
    file_data_node_t* get_data_node();
    file_data_node_t* read_data_node();
    file_data_node_t* append_data_node();
    file_mht_node_t* get_mht_node();
    file_mht_node_t* read_mht_node(uint64_t mht_node_number);
    file_mht_node_t* append_mht_node(uint64_t mht_node_number);
    bool write_recovery_file();
    bool set_update_flag(bool flush_to_disk);
    void clear_update_flag();
    bool update_all_data_and_mht_nodes();
    bool update_meta_data_node();
    bool write_all_changes_to_disk(bool flush_to_disk);
    void erase_recovery_file();
    bool internal_flush(/*bool mc,*/ bool flush_to_disk);

    protected_fs_file(const char* filename, const char* mode, const sgx_aes_gcm_128bit_key_t* import_key, const sgx_aes_gcm_128bit_key_t* kdk_key);

    size_t write(const void* ptr, size_t size, size_t count);
    size_t read(void* ptr, size_t size, size_t count);
    int64_t tell();
    int seek(int64_t new_offset, int origin);
    bool get_eof();
    uint32_t get_error();
    void clear_error();
    int32_t clear_cache();
    bool flush(/*bool mc*/);
    bool pre_close(sgx_key_128bit_t* key, bool import);
    static int32_t remove(const char* filename);