1 use crate::std::error;
2 use crate::std::fmt;
3 use crate::std::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
4 use crate::std::net::{Ipv4Addr, Ipv6Addr, Shutdown, SocketAddr, ToSocketAddrs};
5 use crate::std::sync::Arc;
6 use crate::std::sys::fd::FileDesc;
7 use crate::std::sys::{sgx_ineffective, unsupported, AsInner, FromInner, IntoInner, TryIntoInner};
8 use crate::std::time::Duration;
9
10 use super::abi::usercalls;
11
12 const DEFAULT_FAKE_TTL: u32 = 64;
13
14 #[derive(Debug, Clone)]
15 pub struct Socket {
16 inner: Arc<FileDesc>,
17 local_addr: Option<String>,
18 }
19
20 impl Socket {
new(fd: usercalls::raw::Fd, local_addr: String) -> Socket21 fn new(fd: usercalls::raw::Fd, local_addr: String) -> Socket {
22 Socket {
23 inner: Arc::new(FileDesc::new(fd)),
24 local_addr: Some(local_addr),
25 }
26 }
27 }
28
29 impl AsInner<FileDesc> for Socket {
30 #[inline]
as_inner(&self) -> &FileDesc31 fn as_inner(&self) -> &FileDesc {
32 &self.inner
33 }
34 }
35
36 impl TryIntoInner<FileDesc> for Socket {
try_into_inner(self) -> Result<FileDesc, Socket>37 fn try_into_inner(self) -> Result<FileDesc, Socket> {
38 let Socket { inner, local_addr } = self;
39 Arc::try_unwrap(inner).map_err(|inner| Socket { inner, local_addr })
40 }
41 }
42
43 impl FromInner<(FileDesc, Option<String>)> for Socket {
from_inner((inner, local_addr): (FileDesc, Option<String>)) -> Socket44 fn from_inner((inner, local_addr): (FileDesc, Option<String>)) -> Socket {
45 Socket {
46 inner: Arc::new(inner),
47 local_addr,
48 }
49 }
50 }
51
52 #[derive(Clone)]
53 pub struct TcpStream {
54 inner: Socket,
55 peer_addr: Option<String>,
56 }
57
58 impl fmt::Debug for TcpStream {
fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result59 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
60 let mut res = f.debug_struct("TcpStream");
61
62 if let Some(ref addr) = self.inner.local_addr {
63 res.field("addr", addr);
64 }
65
66 if let Some(ref peer) = self.peer_addr {
67 res.field("peer", peer);
68 }
69
70 res.field("fd", &self.inner.inner.as_inner()).finish()
71 }
72 }
73
io_err_to_addr(result: io::Result<&SocketAddr>) -> io::Result<String>74 fn io_err_to_addr(result: io::Result<&SocketAddr>) -> io::Result<String> {
75 match result {
76 Ok(saddr) => Ok(saddr.to_string()),
77 // need to downcast twice because io::Error::into_inner doesn't return the original
78 // value if the conversion fails
79 Err(e) => {
80 if e.get_ref()
81 .and_then(|e| e.downcast_ref::<NonIpSockAddr>())
82 .is_some()
83 {
84 Ok(e.into_inner()
85 .unwrap()
86 .downcast::<NonIpSockAddr>()
87 .unwrap()
88 .host)
89 } else {
90 Err(e)
91 }
92 }
93 }
94 }
95
addr_to_sockaddr(addr: &Option<String>) -> io::Result<SocketAddr>96 fn addr_to_sockaddr(addr: &Option<String>) -> io::Result<SocketAddr> {
97 addr.as_ref()
98 .ok_or(io::ErrorKind::AddrNotAvailable)?
99 .to_socket_addrs()
100 // unwrap OK: if an iterator is returned, we're guaranteed to get exactly one entry
101 .map(|mut it| it.next().unwrap())
102 }
103
104 impl TcpStream {
connect(addr: io::Result<&SocketAddr>) -> io::Result<TcpStream>105 pub fn connect(addr: io::Result<&SocketAddr>) -> io::Result<TcpStream> {
106 let addr = io_err_to_addr(addr)?;
107 let (fd, local_addr, peer_addr) = usercalls::connect_stream(&addr)?;
108 Ok(TcpStream {
109 inner: Socket::new(fd, local_addr),
110 peer_addr: Some(peer_addr),
111 })
112 }
113
connect_timeout(addr: &SocketAddr, dur: Duration) -> io::Result<TcpStream>114 pub fn connect_timeout(addr: &SocketAddr, dur: Duration) -> io::Result<TcpStream> {
115 if dur == Duration::default() {
116 return Err(io::const_io_error!(
117 io::ErrorKind::InvalidInput,
118 "cannot set a 0 duration timeout",
119 ));
120 }
121 Self::connect(Ok(addr)) // FIXME: ignoring timeout
122 }
123
set_read_timeout(&self, dur: Option<Duration>) -> io::Result<()>124 pub fn set_read_timeout(&self, dur: Option<Duration>) -> io::Result<()> {
125 match dur {
126 Some(dur) if dur == Duration::default() => {
127 return Err(io::const_io_error!(
128 io::ErrorKind::InvalidInput,
129 "cannot set a 0 duration timeout",
130 ));
131 }
132 _ => sgx_ineffective(()),
133 }
134 }
135
set_write_timeout(&self, dur: Option<Duration>) -> io::Result<()>136 pub fn set_write_timeout(&self, dur: Option<Duration>) -> io::Result<()> {
137 match dur {
138 Some(dur) if dur == Duration::default() => {
139 return Err(io::const_io_error!(
140 io::ErrorKind::InvalidInput,
141 "cannot set a 0 duration timeout",
142 ));
143 }
144 _ => sgx_ineffective(()),
145 }
146 }
147
read_timeout(&self) -> io::Result<Option<Duration>>148 pub fn read_timeout(&self) -> io::Result<Option<Duration>> {
149 sgx_ineffective(None)
150 }
151
write_timeout(&self) -> io::Result<Option<Duration>>152 pub fn write_timeout(&self) -> io::Result<Option<Duration>> {
153 sgx_ineffective(None)
154 }
155
peek(&self, _: &mut [u8]) -> io::Result<usize>156 pub fn peek(&self, _: &mut [u8]) -> io::Result<usize> {
157 Ok(0)
158 }
159
read(&self, buf: &mut [u8]) -> io::Result<usize>160 pub fn read(&self, buf: &mut [u8]) -> io::Result<usize> {
161 self.inner.inner.read(buf)
162 }
163
read_buf(&self, buf: BorrowedCursor<'_>) -> io::Result<()>164 pub fn read_buf(&self, buf: BorrowedCursor<'_>) -> io::Result<()> {
165 self.inner.inner.read_buf(buf)
166 }
167
read_vectored(&self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize>168 pub fn read_vectored(&self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
169 self.inner.inner.read_vectored(bufs)
170 }
171
172 #[inline]
is_read_vectored(&self) -> bool173 pub fn is_read_vectored(&self) -> bool {
174 self.inner.inner.is_read_vectored()
175 }
176
write(&self, buf: &[u8]) -> io::Result<usize>177 pub fn write(&self, buf: &[u8]) -> io::Result<usize> {
178 self.inner.inner.write(buf)
179 }
180
write_vectored(&self, bufs: &[IoSlice<'_>]) -> io::Result<usize>181 pub fn write_vectored(&self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
182 self.inner.inner.write_vectored(bufs)
183 }
184
185 #[inline]
is_write_vectored(&self) -> bool186 pub fn is_write_vectored(&self) -> bool {
187 self.inner.inner.is_write_vectored()
188 }
189
peer_addr(&self) -> io::Result<SocketAddr>190 pub fn peer_addr(&self) -> io::Result<SocketAddr> {
191 addr_to_sockaddr(&self.peer_addr)
192 }
193
socket_addr(&self) -> io::Result<SocketAddr>194 pub fn socket_addr(&self) -> io::Result<SocketAddr> {
195 addr_to_sockaddr(&self.inner.local_addr)
196 }
197
shutdown(&self, _: Shutdown) -> io::Result<()>198 pub fn shutdown(&self, _: Shutdown) -> io::Result<()> {
199 sgx_ineffective(())
200 }
201
duplicate(&self) -> io::Result<TcpStream>202 pub fn duplicate(&self) -> io::Result<TcpStream> {
203 Ok(self.clone())
204 }
205
set_linger(&self, _: Option<Duration>) -> io::Result<()>206 pub fn set_linger(&self, _: Option<Duration>) -> io::Result<()> {
207 sgx_ineffective(())
208 }
209
linger(&self) -> io::Result<Option<Duration>>210 pub fn linger(&self) -> io::Result<Option<Duration>> {
211 sgx_ineffective(None)
212 }
213
set_nodelay(&self, _: bool) -> io::Result<()>214 pub fn set_nodelay(&self, _: bool) -> io::Result<()> {
215 sgx_ineffective(())
216 }
217
nodelay(&self) -> io::Result<bool>218 pub fn nodelay(&self) -> io::Result<bool> {
219 sgx_ineffective(false)
220 }
221
set_ttl(&self, _: u32) -> io::Result<()>222 pub fn set_ttl(&self, _: u32) -> io::Result<()> {
223 sgx_ineffective(())
224 }
225
ttl(&self) -> io::Result<u32>226 pub fn ttl(&self) -> io::Result<u32> {
227 sgx_ineffective(DEFAULT_FAKE_TTL)
228 }
229
take_error(&self) -> io::Result<Option<io::Error>>230 pub fn take_error(&self) -> io::Result<Option<io::Error>> {
231 Ok(None)
232 }
233
set_nonblocking(&self, _: bool) -> io::Result<()>234 pub fn set_nonblocking(&self, _: bool) -> io::Result<()> {
235 sgx_ineffective(())
236 }
237 }
238
239 impl AsInner<Socket> for TcpStream {
240 #[inline]
as_inner(&self) -> &Socket241 fn as_inner(&self) -> &Socket {
242 &self.inner
243 }
244 }
245
246 // `Inner` includes `peer_addr` so that a `TcpStream` maybe correctly
247 // reconstructed if `Socket::try_into_inner` fails.
248 impl IntoInner<(Socket, Option<String>)> for TcpStream {
into_inner(self) -> (Socket, Option<String>)249 fn into_inner(self) -> (Socket, Option<String>) {
250 (self.inner, self.peer_addr)
251 }
252 }
253
254 impl FromInner<(Socket, Option<String>)> for TcpStream {
from_inner((inner, peer_addr): (Socket, Option<String>)) -> TcpStream255 fn from_inner((inner, peer_addr): (Socket, Option<String>)) -> TcpStream {
256 TcpStream { inner, peer_addr }
257 }
258 }
259
260 #[derive(Clone)]
261 pub struct TcpListener {
262 inner: Socket,
263 }
264
265 impl fmt::Debug for TcpListener {
fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result266 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
267 let mut res = f.debug_struct("TcpListener");
268
269 if let Some(ref addr) = self.inner.local_addr {
270 res.field("addr", addr);
271 }
272
273 res.field("fd", &self.inner.inner.as_inner()).finish()
274 }
275 }
276
277 impl TcpListener {
bind(addr: io::Result<&SocketAddr>) -> io::Result<TcpListener>278 pub fn bind(addr: io::Result<&SocketAddr>) -> io::Result<TcpListener> {
279 let addr = io_err_to_addr(addr)?;
280 let (fd, local_addr) = usercalls::bind_stream(&addr)?;
281 Ok(TcpListener {
282 inner: Socket::new(fd, local_addr),
283 })
284 }
285
socket_addr(&self) -> io::Result<SocketAddr>286 pub fn socket_addr(&self) -> io::Result<SocketAddr> {
287 addr_to_sockaddr(&self.inner.local_addr)
288 }
289
accept(&self) -> io::Result<(TcpStream, SocketAddr)>290 pub fn accept(&self) -> io::Result<(TcpStream, SocketAddr)> {
291 let (fd, local_addr, peer_addr) = usercalls::accept_stream(self.inner.inner.raw())?;
292 let peer_addr = Some(peer_addr);
293 let ret_peer = addr_to_sockaddr(&peer_addr).unwrap_or_else(|_| ([0; 4], 0).into());
294 Ok((
295 TcpStream {
296 inner: Socket::new(fd, local_addr),
297 peer_addr,
298 },
299 ret_peer,
300 ))
301 }
302
duplicate(&self) -> io::Result<TcpListener>303 pub fn duplicate(&self) -> io::Result<TcpListener> {
304 Ok(self.clone())
305 }
306
set_ttl(&self, _: u32) -> io::Result<()>307 pub fn set_ttl(&self, _: u32) -> io::Result<()> {
308 sgx_ineffective(())
309 }
310
ttl(&self) -> io::Result<u32>311 pub fn ttl(&self) -> io::Result<u32> {
312 sgx_ineffective(DEFAULT_FAKE_TTL)
313 }
314
set_only_v6(&self, _: bool) -> io::Result<()>315 pub fn set_only_v6(&self, _: bool) -> io::Result<()> {
316 sgx_ineffective(())
317 }
318
only_v6(&self) -> io::Result<bool>319 pub fn only_v6(&self) -> io::Result<bool> {
320 sgx_ineffective(false)
321 }
322
take_error(&self) -> io::Result<Option<io::Error>>323 pub fn take_error(&self) -> io::Result<Option<io::Error>> {
324 Ok(None)
325 }
326
set_nonblocking(&self, _: bool) -> io::Result<()>327 pub fn set_nonblocking(&self, _: bool) -> io::Result<()> {
328 sgx_ineffective(())
329 }
330 }
331
332 impl AsInner<Socket> for TcpListener {
333 #[inline]
as_inner(&self) -> &Socket334 fn as_inner(&self) -> &Socket {
335 &self.inner
336 }
337 }
338
339 impl IntoInner<Socket> for TcpListener {
into_inner(self) -> Socket340 fn into_inner(self) -> Socket {
341 self.inner
342 }
343 }
344
345 impl FromInner<Socket> for TcpListener {
from_inner(inner: Socket) -> TcpListener346 fn from_inner(inner: Socket) -> TcpListener {
347 TcpListener { inner }
348 }
349 }
350
351 pub struct UdpSocket(!);
352
353 impl UdpSocket {
bind(_: io::Result<&SocketAddr>) -> io::Result<UdpSocket>354 pub fn bind(_: io::Result<&SocketAddr>) -> io::Result<UdpSocket> {
355 unsupported()
356 }
357
peer_addr(&self) -> io::Result<SocketAddr>358 pub fn peer_addr(&self) -> io::Result<SocketAddr> {
359 self.0
360 }
361
socket_addr(&self) -> io::Result<SocketAddr>362 pub fn socket_addr(&self) -> io::Result<SocketAddr> {
363 self.0
364 }
365
recv_from(&self, _: &mut [u8]) -> io::Result<(usize, SocketAddr)>366 pub fn recv_from(&self, _: &mut [u8]) -> io::Result<(usize, SocketAddr)> {
367 self.0
368 }
369
peek_from(&self, _: &mut [u8]) -> io::Result<(usize, SocketAddr)>370 pub fn peek_from(&self, _: &mut [u8]) -> io::Result<(usize, SocketAddr)> {
371 self.0
372 }
373
send_to(&self, _: &[u8], _: &SocketAddr) -> io::Result<usize>374 pub fn send_to(&self, _: &[u8], _: &SocketAddr) -> io::Result<usize> {
375 self.0
376 }
377
duplicate(&self) -> io::Result<UdpSocket>378 pub fn duplicate(&self) -> io::Result<UdpSocket> {
379 self.0
380 }
381
set_read_timeout(&self, _: Option<Duration>) -> io::Result<()>382 pub fn set_read_timeout(&self, _: Option<Duration>) -> io::Result<()> {
383 self.0
384 }
385
set_write_timeout(&self, _: Option<Duration>) -> io::Result<()>386 pub fn set_write_timeout(&self, _: Option<Duration>) -> io::Result<()> {
387 self.0
388 }
389
read_timeout(&self) -> io::Result<Option<Duration>>390 pub fn read_timeout(&self) -> io::Result<Option<Duration>> {
391 self.0
392 }
393
write_timeout(&self) -> io::Result<Option<Duration>>394 pub fn write_timeout(&self) -> io::Result<Option<Duration>> {
395 self.0
396 }
397
set_broadcast(&self, _: bool) -> io::Result<()>398 pub fn set_broadcast(&self, _: bool) -> io::Result<()> {
399 self.0
400 }
401
broadcast(&self) -> io::Result<bool>402 pub fn broadcast(&self) -> io::Result<bool> {
403 self.0
404 }
405
set_multicast_loop_v4(&self, _: bool) -> io::Result<()>406 pub fn set_multicast_loop_v4(&self, _: bool) -> io::Result<()> {
407 self.0
408 }
409
multicast_loop_v4(&self) -> io::Result<bool>410 pub fn multicast_loop_v4(&self) -> io::Result<bool> {
411 self.0
412 }
413
set_multicast_ttl_v4(&self, _: u32) -> io::Result<()>414 pub fn set_multicast_ttl_v4(&self, _: u32) -> io::Result<()> {
415 self.0
416 }
417
multicast_ttl_v4(&self) -> io::Result<u32>418 pub fn multicast_ttl_v4(&self) -> io::Result<u32> {
419 self.0
420 }
421
set_multicast_loop_v6(&self, _: bool) -> io::Result<()>422 pub fn set_multicast_loop_v6(&self, _: bool) -> io::Result<()> {
423 self.0
424 }
425
multicast_loop_v6(&self) -> io::Result<bool>426 pub fn multicast_loop_v6(&self) -> io::Result<bool> {
427 self.0
428 }
429
join_multicast_v4(&self, _: &Ipv4Addr, _: &Ipv4Addr) -> io::Result<()>430 pub fn join_multicast_v4(&self, _: &Ipv4Addr, _: &Ipv4Addr) -> io::Result<()> {
431 self.0
432 }
433
join_multicast_v6(&self, _: &Ipv6Addr, _: u32) -> io::Result<()>434 pub fn join_multicast_v6(&self, _: &Ipv6Addr, _: u32) -> io::Result<()> {
435 self.0
436 }
437
leave_multicast_v4(&self, _: &Ipv4Addr, _: &Ipv4Addr) -> io::Result<()>438 pub fn leave_multicast_v4(&self, _: &Ipv4Addr, _: &Ipv4Addr) -> io::Result<()> {
439 self.0
440 }
441
leave_multicast_v6(&self, _: &Ipv6Addr, _: u32) -> io::Result<()>442 pub fn leave_multicast_v6(&self, _: &Ipv6Addr, _: u32) -> io::Result<()> {
443 self.0
444 }
445
set_ttl(&self, _: u32) -> io::Result<()>446 pub fn set_ttl(&self, _: u32) -> io::Result<()> {
447 self.0
448 }
449
ttl(&self) -> io::Result<u32>450 pub fn ttl(&self) -> io::Result<u32> {
451 self.0
452 }
453
take_error(&self) -> io::Result<Option<io::Error>>454 pub fn take_error(&self) -> io::Result<Option<io::Error>> {
455 self.0
456 }
457
set_nonblocking(&self, _: bool) -> io::Result<()>458 pub fn set_nonblocking(&self, _: bool) -> io::Result<()> {
459 self.0
460 }
461
recv(&self, _: &mut [u8]) -> io::Result<usize>462 pub fn recv(&self, _: &mut [u8]) -> io::Result<usize> {
463 self.0
464 }
465
peek(&self, _: &mut [u8]) -> io::Result<usize>466 pub fn peek(&self, _: &mut [u8]) -> io::Result<usize> {
467 self.0
468 }
469
send(&self, _: &[u8]) -> io::Result<usize>470 pub fn send(&self, _: &[u8]) -> io::Result<usize> {
471 self.0
472 }
473
connect(&self, _: io::Result<&SocketAddr>) -> io::Result<()>474 pub fn connect(&self, _: io::Result<&SocketAddr>) -> io::Result<()> {
475 self.0
476 }
477 }
478
479 impl fmt::Debug for UdpSocket {
fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result480 fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
481 self.0
482 }
483 }
484
485 #[derive(Debug)]
486 pub struct NonIpSockAddr {
487 host: String,
488 }
489
490 impl error::Error for NonIpSockAddr {
491 #[allow(deprecated)]
description(&self) -> &str492 fn description(&self) -> &str {
493 "Failed to convert address to SocketAddr"
494 }
495 }
496
497 impl fmt::Display for NonIpSockAddr {
fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result498 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
499 write!(f, "Failed to convert address to SocketAddr: {}", self.host)
500 }
501 }
502
503 pub struct LookupHost(!);
504
505 impl LookupHost {
new(host: String) -> io::Result<LookupHost>506 fn new(host: String) -> io::Result<LookupHost> {
507 Err(io::Error::new(
508 io::ErrorKind::Uncategorized,
509 NonIpSockAddr { host },
510 ))
511 }
512
port(&self) -> u16513 pub fn port(&self) -> u16 {
514 self.0
515 }
516 }
517
518 impl Iterator for LookupHost {
519 type Item = SocketAddr;
next(&mut self) -> Option<SocketAddr>520 fn next(&mut self) -> Option<SocketAddr> {
521 self.0
522 }
523 }
524
525 impl TryFrom<&str> for LookupHost {
526 type Error = io::Error;
527
try_from(v: &str) -> io::Result<LookupHost>528 fn try_from(v: &str) -> io::Result<LookupHost> {
529 LookupHost::new(v.to_owned())
530 }
531 }
532
533 impl<'a> TryFrom<(&'a str, u16)> for LookupHost {
534 type Error = io::Error;
535
try_from((host, port): (&'a str, u16)) -> io::Result<LookupHost>536 fn try_from((host, port): (&'a str, u16)) -> io::Result<LookupHost> {
537 LookupHost::new(format!("{host}:{port}"))
538 }
539 }
540
541 #[allow(bad_style)]
542 pub mod netc {
543 pub const AF_INET: u8 = 0;
544 pub const AF_INET6: u8 = 1;
545 pub type sa_family_t = u8;
546
547 #[derive(Copy, Clone)]
548 pub struct in_addr {
549 pub s_addr: u32,
550 }
551
552 #[derive(Copy, Clone)]
553 pub struct sockaddr_in {
554 pub sin_family: sa_family_t,
555 pub sin_port: u16,
556 pub sin_addr: in_addr,
557 }
558
559 #[derive(Copy, Clone)]
560 pub struct in6_addr {
561 pub s6_addr: [u8; 16],
562 }
563
564 #[derive(Copy, Clone)]
565 pub struct sockaddr_in6 {
566 pub sin6_family: sa_family_t,
567 pub sin6_port: u16,
568 pub sin6_addr: in6_addr,
569 pub sin6_flowinfo: u32,
570 pub sin6_scope_id: u32,
571 }
572
573 #[derive(Copy, Clone)]
574 pub struct sockaddr {}
575 }
576