Skip to main content

report_test/
lib.rs

1/* Copyright (c) Fortanix, Inc.
2 *
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
7#![doc(html_logo_url = "https://edp.fortanix.com/img/docs/edp-logo.svg",
8       html_favicon_url = "https://edp.fortanix.com/favicon.ico",
9       html_root_url = "https://edp.fortanix.com/docs/api/")]
10
11extern crate enclave_runner;
12extern crate enclave_runner_sgx;
13extern crate anyhow;
14extern crate sgx_isa;
15extern crate sgxs;
16
17use anyhow::Context;
18use enclave_runner::EnclaveBuilder;
19use enclave_runner_sgx::EnclaveBuilder as EnclaveBuilderSgx;
20use sgx_isa::{PageType, Report, SecinfoFlags, Targetinfo, Attributes, AttributesFlags, Miscselect};
21use sgxs::loader::Load;
22use sgxs::sgxs::{PageChunk, SecinfoTruncated, SgxsWrite};
23
24pub struct ReportBuilder {
25    enclave_bytes: Vec<u8>,
26    attributes: Option<Attributes>,
27    miscselect: Option<Miscselect>,
28}
29
30impl ReportBuilder {
31    pub fn new(targetinfo: &Targetinfo) -> ReportBuilder {
32        let mut report_enclave = include_bytes!("../enclave/report.sgxs").to_vec();
33        let mut targetinfo: &[u8] = targetinfo.as_ref();
34        let secinfo = SecinfoTruncated {
35            flags: SecinfoFlags::R | SecinfoFlags::W | PageType::Reg.into(),
36        };
37        report_enclave
38            .write_page(
39                (&mut targetinfo, [PageChunk::Included; 16]),
40                0x3000,
41                secinfo,
42            )
43            .unwrap();
44
45        ReportBuilder {
46            enclave_bytes: report_enclave,
47            attributes: None,
48            miscselect: None
49        }
50    }
51
52    pub fn attributes(mut self, mut attributes: Attributes) -> Self {
53        attributes.flags |= AttributesFlags::MODE64BIT;
54        self.attributes = Some(attributes);
55        self
56    }
57
58    pub fn miscselect(mut self, miscselect: Miscselect) -> Self {
59        self.miscselect = Some(miscselect);
60        self
61    }
62
63    pub fn build<L: Load>(self, enclave_loader: &mut L) -> Result<Report, anyhow::Error> {
64        let mut builder = EnclaveBuilderSgx::new_from_memory(&self.enclave_bytes);
65
66        if let Some(attributes) = self.attributes {
67            builder.attributes(attributes);
68        }
69
70        if let Some(miscselect) = self.miscselect {
71            builder.miscselect(miscselect);
72        }
73
74        unsafe {
75            let mut report = Report::default();
76
77            EnclaveBuilder::<_, enclave_runner::Library>::new(builder)
78                .build(enclave_loader)
79                .context("failed to load report enclave")?
80                .call(&mut report as *mut _ as _, 0, 0, 0, 0)
81                .context("failed to call report enclave")?;
82            Ok(report)
83        }
84    }
85}
86
87pub fn report<L: Load>(targetinfo: &Targetinfo, enclave_loader: &mut L) -> Result<Report, anyhow::Error> {
88    ReportBuilder::new(targetinfo).build(enclave_loader)
89}