optee_utee/
time.rs

1// Licensed to the Apache Software Foundation (ASF) under one
2// or more contributor license agreements.  See the NOTICE file
3// distributed with this work for additional information
4// regarding copyright ownership.  The ASF licenses this file
5// to you under the Apache License, Version 2.0 (the
6// "License"); you may not use this file except in compliance
7// with the License.  You may obtain a copy of the License at
8//
9//   http://www.apache.org/licenses/LICENSE-2.0
10//
11// Unless required by applicable law or agreed to in writing,
12// software distributed under the License is distributed on an
13// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14// KIND, either express or implied.  See the License for the
15// specific language governing permissions and limitations
16// under the License.
17
18use crate::{Error, Result};
19use core::fmt;
20use optee_utee_sys as raw;
21
22/// A millisecond resolution structure for saving the time.
23pub struct Time {
24    /// The field for the seconds.
25    pub seconds: u32,
26    /// The field for the milliseconds within this second.
27    pub millis: u32,
28}
29
30impl Default for Time {
31    fn default() -> Self {
32        Self::new()
33    }
34}
35
36impl Time {
37    /// Create a new empty time structure.
38    pub fn new() -> Self {
39        Time {
40            seconds: 0,
41            millis: 0,
42        }
43    }
44
45    /// Retrieve the current system time.
46    /// The origin of this system time is arbitrary and implementation-dependent.
47    /// Different TA instances may even have different system times.
48    /// The only guarantee is that the system time is not reset or rolled back during the life of a
49    /// given TA instance, so it can be used to compute time differences and operation deadlines.
50    ///
51    /// # Example
52    ///
53    /// ``` rust,no_run
54    /// # use optee_utee::Time;
55    /// let mut time = Time::new();
56    /// time.system_time();
57    /// ```
58    ///
59    /// # Panics
60    ///
61    /// 1) If the Implementation detects any error.
62    pub fn system_time(&mut self) {
63        unsafe {
64            raw::TEE_GetSystemTime(self as *mut _ as _);
65        }
66    }
67
68    /// Wait  for the specified number of milliseconds or wait forever if timeout equals
69    /// `raw::TEE_TIMEOUT_INFINITE` (0xFFFFFFFF). The waiting timer is `System Time`.
70    ///
71    /// # Parameters
72    ///
73    /// 1) `timeout`: The number of milliseconds to wait, or `raw::TEE_TIMEOUT_INFINITE`.
74    ///
75    /// # Example
76    ///
77    /// ``` rust,no_run
78    /// # use optee_utee::{Time, Result};
79    /// # fn main() -> Result<()> {
80    /// Time::wait(1000)?;
81    /// # Ok(())
82    /// # }
83    /// ```
84    ///
85    /// # Errors
86    ///
87    /// 1) `Cancel`: If the wait has been cancelled.
88    ///
89    /// # Panics
90    ///
91    /// 1) If the Implementation detects any error.
92    pub fn wait(timeout: u32) -> Result<()> {
93        match unsafe { raw::TEE_Wait(timeout) } {
94            raw::TEE_SUCCESS => Ok(()),
95            code => Err(Error::from_raw_error(code)),
96        }
97    }
98
99    /// Retrieve the persisten time of the Trusted Application. Since the timer is not
100    /// automatically set, this function should be called after [set_ta_time](Time::set_ta_time).
101    /// The time is a real-time source of time and the origin of this time is set individually by each Trusted Application.
102    /// Also, the time SHALL persist across reboots.
103    ///
104    /// # Example
105    ///
106    /// ``` rust,no_run
107    /// # use optee_utee::{Time, Result};
108    /// # fn main() -> Result<()> {
109    /// let mut time = Time::new();
110    /// time.system_time();
111    /// time.set_ta_time()?;
112    /// time.ta_time()?;
113    /// # Ok(())
114    /// # }
115    /// ```
116    ///
117    /// # Errors
118    ///
119    /// 1) `TimeNotSet`: Time is not set.
120    /// 2) `TimeNeedsReset`: Time needs to be reset.
121    /// 3) `Overflow`: The number of seconds in the TA Persistent Time overflows the range of a
122    ///    `u32`. The field `seconds` is still set to the TA Persistent Time truncated to 32 bits.
123    ///
124    /// # Panics
125    ///
126    /// 1) If the Implementation detects any error.
127    pub fn ta_time(&mut self) -> Result<()> {
128        match unsafe { raw::TEE_GetTAPersistentTime(self as *mut _ as _) } {
129            raw::TEE_SUCCESS => Ok(()),
130            code => Err(Error::from_raw_error(code)),
131        }
132    }
133
134    /// Set the persistent time of the current Trusted Application.
135    ///
136    /// # Errors
137    ///
138    /// 1) `OutOfMemory`: If not enough memory is available to complete the operation.
139    /// 2) `SotrageNoSpace`: If insufficient storage space is available to complete the operation.
140    ///
141    /// # Panics
142    ///
143    /// 1) If the Implementation detects any error.
144    pub fn set_ta_time(&self) -> Result<()> {
145        match unsafe { raw::TEE_SetTAPersistentTime(self as *const _ as _) } {
146            raw::TEE_SUCCESS => Ok(()),
147            code => Err(Error::from_raw_error(code)),
148        }
149    }
150
151    /// Retrieve the current REE system time.
152    /// The time is as trusted as the REE itself and may also be tampered by the user.
153    ///
154    /// Panics
155    ///
156    /// 1) If the Implementation detects any error.
157    pub fn ree_time(&mut self) {
158        unsafe {
159            raw::TEE_GetREETime(self as *mut _ as _);
160        }
161    }
162}
163
164impl fmt::Display for Time {
165    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
166        write!(
167            f,
168            "(second: {}, millisecond: {})",
169            self.seconds, self.millis
170        )
171    }
172}