optee_utee/net/socket.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 optee_utee_sys as raw;
19
20use super::SocketError;
21use core::time::Duration;
22
23/// A trait designed to accommodate various implementations of GP TEE Sockets
24/// API.
25///
26/// An implementation of this trait is responsible for handling all
27/// protocol-related tasks, including but not limited to:
28/// * Defining its own Setup type and using it to establish a new connection;
29/// * Sending and receiving data over the connection, while managing protocol
30/// errors (such as permitting certain warnings but raising others).
31pub trait SocketAdapter: Sized {
32 type Setup;
33 type Handle;
34
35 fn open(setup: Self::Setup) -> Result<Self::Handle, SocketError>;
36 fn send(handle: &mut Self::Handle, buf: &[u8], timeout: u32) -> Result<usize, SocketError>;
37 fn recv(handle: &mut Self::Handle, buf: &mut [u8], timeout: u32) -> Result<usize, SocketError>;
38}
39
40/// A struct used for socket operations.
41pub struct Socket<T: SocketAdapter> {
42 handle: T::Handle,
43 recv_timeout: u32,
44 send_timeout: u32,
45}
46
47impl<T: SocketAdapter> Socket<T> {
48 /// create a new connection, and then sending and receiving data over it.
49 pub fn open(setup: T::Setup) -> Result<Self, SocketError> {
50 let handle = T::open(setup)?;
51 Ok(Self {
52 handle,
53 recv_timeout: raw::TEE_TIMEOUT_INFINITE,
54 send_timeout: raw::TEE_TIMEOUT_INFINITE,
55 })
56 }
57 /// set timeout of recv operation.
58 pub fn set_recv_timeout_in_milli(&mut self, milliseconds: u32) {
59 self.recv_timeout = milliseconds;
60 }
61 /// set timeout of send operation.
62 pub fn set_send_timeout_in_milli(&mut self, milliseconds: u32) {
63 self.send_timeout = milliseconds;
64 }
65 /// a wrapper of `set_recv_timeout_in_milli`, similar to `set_read_timeout`
66 /// in std::net::TcpStream, it will set timeout to `TEE_TIMEOUT_INFINITE`
67 /// if `Option::None` is provided.
68 pub fn set_recv_timeout(&mut self, dur: Option<Duration>) -> crate::Result<()> {
69 let milliseconds = convert_duration_option_to_timeout(dur)?;
70 self.set_recv_timeout_in_milli(milliseconds);
71 Ok(())
72 }
73 /// a wrapper of `set_send_timeout_in_milli`, similar to
74 /// `set_write_timeout` in std::net::TcpStream, it will set timeout to
75 /// `TEE_TIMEOUT_INFINITE` if `Option::None` is provided.
76 pub fn set_send_timeout(&mut self, dur: Option<Duration>) -> crate::Result<()> {
77 let milliseconds = convert_duration_option_to_timeout(dur)?;
78 self.set_send_timeout_in_milli(milliseconds);
79 Ok(())
80 }
81 /// send data, similar to `write` in `io::Write`
82 pub fn send(&mut self, buf: &[u8]) -> Result<usize, SocketError> {
83 T::send(&mut self.handle, buf, self.send_timeout)
84 }
85 /// recv data, similar to `read` in `io::Read`
86 pub fn recv(&mut self, buf: &mut [u8]) -> Result<usize, SocketError> {
87 T::recv(&mut self.handle, buf, self.recv_timeout)
88 }
89}
90
91fn convert_duration_option_to_timeout(dur: Option<Duration>) -> crate::Result<u32> {
92 match dur {
93 None => Ok(raw::TEE_TIMEOUT_INFINITE),
94 Some(v) => {
95 let milliseconds = v.as_millis();
96 if milliseconds > (u32::MAX as u128) {
97 return Err(crate::ErrorKind::BadParameters.into());
98 }
99 Ok(milliseconds as u32)
100 }
101 }
102}