Skip to main content

rust_utee/
trace.rs

1use crate::syscalls::syscall_table::_utee_log;
2use core::ffi::*;
3use core::fmt::{Arguments, Result, Write};
4
5pub const TRACE_MIN: i32 = 0;
6pub const TRACE_ERROR: i32 = 1;
7pub const TRACE_INFO: i32 = 2;
8pub const TRACE_DEBUG: i32 = 3;
9pub const TRACE_FLOW: i32 = 4;
10pub const TRACE_MAX: i32 = TRACE_FLOW;
11pub const TRACE_PRINTF_LEVEL: i32 = TRACE_ERROR;
12
13pub const DEFAULT_TRACE_LEVEL: i32 = {
14    if cfg!(feature = "trace-error") {
15        TRACE_ERROR
16    } else if cfg!(feature = "trace-flow") {
17        TRACE_FLOW
18    } else if cfg!(feature = "trace-info") {
19        TRACE_INFO
20    } else if cfg!(feature = "trace-debug") {
21        TRACE_DEBUG
22    } else {
23        TRACE_MAX
24    }
25};
26
27use core::sync::atomic::{AtomicI32, Ordering};
28
29static TRACE_LEVEL: AtomicI32 = AtomicI32::new(DEFAULT_TRACE_LEVEL);
30
31pub struct Trace;
32
33impl Trace {
34    fn new() -> Self {
35        Trace {}
36    }
37
38    pub fn _print(fmt: Arguments) {
39        let mut writer = Trace::new();
40        let result = writer.write_fmt(fmt);
41
42        if let Err(e) = result {
43            panic!("failed printing to trace: {}", e);
44        }
45    }
46
47    pub fn set_level(level: i32) {
48        let val = if level >= TRACE_MIN && level <= TRACE_MAX {
49            level
50        } else {
51            TRACE_MAX
52        };
53        TRACE_LEVEL.store(val, Ordering::Relaxed);
54    }
55
56    pub fn get_level() -> i32 {
57        TRACE_LEVEL.load(Ordering::Relaxed)
58    }
59}
60
61impl Write for Trace {
62    fn write_str(&mut self, buf: &str) -> Result {
63        _utee_log(buf.as_ptr() as *const c_void, buf.len());
64        Ok(())
65    }
66}