sirenia: Switch over to libchromeos-rs's vsock implementation.

This required adding #[derive(Debug)] in some parts of
libchromeos::vsock.

BUG=b:144915425
TEST=cargo test

Change-Id: I2f25bb93cc748ac5f82399231d60ac976e987cec
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform2/+/2337149
Tested-by: Allen Webb <allenwebb@google.com>
Reviewed-by: Dylan Reid <dgreid@chromium.org>
Reviewed-by: Stephen Barber <smbarber@chromium.org>
diff --git a/libchromeos-rs/src/vsock.rs b/libchromeos-rs/src/vsock.rs
index f96a0f8..b4fa589 100644
--- a/libchromeos-rs/src/vsock.rs
+++ b/libchromeos-rs/src/vsock.rs
@@ -48,7 +48,7 @@
 }
 
 /// An address associated with a virtual socket.
-#[derive(Copy, Clone)]
+#[derive(Debug, Copy, Clone)]
 pub struct SocketAddr {
     pub cid: c_uint,
     pub port: c_uint,
@@ -123,6 +123,7 @@
 }
 
 /// A virtual stream socket.
+#[derive(Debug)]
 pub struct VsockStream {
     fd: RawFd,
 }
@@ -244,6 +245,7 @@
 }
 
 /// Represents a virtual socket server.
+#[derive(Debug)]
 pub struct VsockListener {
     fd: RawFd,
 }
diff --git a/sirenia/Cargo.toml b/sirenia/Cargo.toml
index 7cda6b5..5716188 100644
--- a/sirenia/Cargo.toml
+++ b/sirenia/Cargo.toml
@@ -20,5 +20,6 @@
 [dependencies]
 getopts = "0.2"
 libc = "0.2.44"
+libchromeos = { path = "../libchromeos-rs" } # provided by ebuild
 minijail = { path = "../../aosp/external/minijail/rust/minijail" } # provided by ebuild
 sys_util = { path = "../../platform/crosvm/sys_util" } # provided by ebuild
diff --git a/sirenia/src/to_sys_util/mod.rs b/sirenia/src/to_sys_util/mod.rs
index aad573c..d52d3d2 100644
--- a/sirenia/src/to_sys_util/mod.rs
+++ b/sirenia/src/to_sys_util/mod.rs
@@ -8,32 +8,17 @@
 //!
 //! TODO(b/162502718) Move this over to crosvm/sys_util
 
-use std::fs::File;
 use std::io;
-use std::mem::{size_of, MaybeUninit};
-use std::net::TcpStream;
-use std::os::unix::io::{AsRawFd, FromRawFd, RawFd};
+use std::mem::MaybeUninit;
 use std::ptr::null_mut;
 
 use libc::{
-    self, accept4, bind, c_int, connect, listen, sigfillset, sigprocmask, sigset_t, sockaddr_vm,
-    socket, socklen_t, wait, AF_VSOCK, ECHILD, SIG_BLOCK, SIG_UNBLOCK, SOCK_CLOEXEC, SOCK_STREAM,
-    SOMAXCONN, VMADDR_CID_ANY, VMADDR_CID_HOST, VMADDR_CID_HYPERVISOR,
+    self, c_int, sigfillset, sigprocmask, sigset_t, wait, ECHILD, SIG_BLOCK, SIG_UNBLOCK,
+    VMADDR_CID_ANY, VMADDR_CID_HOST, VMADDR_CID_HYPERVISOR,
 };
-use sys_util::handle_eintr_errno;
 
 const VMADDR_CID_LOCAL: u32 = 1;
 
-pub const VMADDR_PORT_ANY: u32 = libc::VMADDR_PORT_ANY;
-
-const DEFAULT_SOCKADDR_VM: sockaddr_vm = sockaddr_vm {
-    svm_family: 0,
-    svm_reserved1: 0,
-    svm_port: 0,
-    svm_cid: 0,
-    svm_zero: [0; 4],
-};
-
 pub fn errno() -> c_int {
     io::Error::last_os_error().raw_os_error().unwrap()
 }
@@ -88,26 +73,6 @@
     }
 }
 
-fn get_vsock_stream() -> Result<RawFd, io::Error> {
-    // This is safe because it doesn't take any references.
-    let fd: RawFd = handle_eintr_errno!(unsafe { socket(AF_VSOCK, SOCK_STREAM | SOCK_CLOEXEC, 0) });
-    if fd < 0 {
-        Err(io::Error::last_os_error())
-    } else {
-        Ok(fd)
-    }
-}
-
-fn new_vsock_addr(cid: VsockCid, port: u32) -> sockaddr_vm {
-    let mut addr: sockaddr_vm = DEFAULT_SOCKADDR_VM.clone();
-
-    addr.svm_family = AF_VSOCK as u16;
-    addr.svm_port = port;
-    addr.svm_cid = cid.into();
-
-    addr
-}
-
 #[derive(Debug, Copy, Clone)]
 pub enum VsockCid {
     Any,
@@ -140,91 +105,3 @@
         }
     }
 }
-
-pub struct VsockStreamListener(File);
-
-impl VsockStreamListener {
-    pub fn new(cid: VsockCid, port: u32) -> Result<Self, io::Error> {
-        // This is safe because the fd is valid and not associated with a rust
-        // struct yet.
-        let fd = unsafe { File::from_raw_fd(get_vsock_stream()?) };
-        let addr = new_vsock_addr(cid, port);
-
-        // This is safe because the passed structs will outlive the bind
-        // call.
-        if handle_eintr_errno!(unsafe {
-            bind(
-                fd.as_raw_fd(),
-                &addr as *const _ as *const _,
-                size_of::<sockaddr_vm>() as socklen_t,
-            )
-        }) != 0
-        {
-            return Err(io::Error::last_os_error());
-        }
-
-        // This is safe because the file descriptor is owned.
-        if handle_eintr_errno!(unsafe { listen(fd.as_raw_fd(), SOMAXCONN) }) != 0 {
-            return Err(io::Error::last_os_error());
-        }
-
-        Ok(VsockStreamListener(fd))
-    }
-
-    pub fn accept(&self) -> Result<(TcpStream, (VsockCid, u32)), io::Error> {
-        let mut addr: sockaddr_vm = DEFAULT_SOCKADDR_VM.clone();
-        let mut len: socklen_t = size_of::<sockaddr_vm>() as socklen_t;
-        let stream: TcpStream;
-
-        // This is safe because the passed structs will outlive the accept4
-        // call and if the resulting file descriptor is valid it is wrapped
-        // with a type that will close it when dropped.
-        let fd: c_int = handle_eintr_errno!(unsafe {
-            accept4(
-                self.0.as_raw_fd(),
-                &mut addr as *mut _ as *mut _,
-                &mut len as *mut _,
-                SOCK_CLOEXEC,
-            )
-        });
-        if fd < 0 {
-            return Err(io::Error::last_os_error());
-        }
-
-        // This is safe because the file descriptor is valid and isn't
-        // associated with a rust struct yet.
-        stream = unsafe { TcpStream::from_raw_fd(fd) };
-        if size_of::<sockaddr_vm>() as socklen_t != len {
-            return Err(io::Error::last_os_error());
-        }
-        Ok((stream, (VsockCid::from(addr.svm_cid), addr.svm_port)))
-    }
-}
-
-pub fn vsock_connect(cid: VsockCid, port: u32) -> Result<TcpStream, io::Error> {
-    let fd: RawFd = get_vsock_stream()?;
-    let addr: sockaddr_vm = new_vsock_addr(cid, port);
-
-    if handle_eintr_errno!(unsafe {
-        // This is safe because the passed structs will outlive the connect
-        // call.
-        connect(
-            fd,
-            &addr as *const _ as *const _,
-            size_of::<sockaddr_vm>() as socklen_t,
-        )
-    }) != 0
-    {
-        // This is safe because the file descriptor is valid and isn't
-        // associated with a rust struct yet. It is used to close the
-        // file descriptor.
-        unsafe {
-            File::from_raw_fd(fd);
-        }
-        return Err(io::Error::last_os_error());
-    }
-
-    // This is safe because the file descriptor is valid and isn't associated
-    // with a rust struct yet.
-    Ok(unsafe { TcpStream::from_raw_fd(fd) })
-}
diff --git a/sirenia/src/transport/mod.rs b/sirenia/src/transport/mod.rs
index c944901..a9321b2 100644
--- a/sirenia/src/transport/mod.rs
+++ b/sirenia/src/transport/mod.rs
@@ -16,9 +16,10 @@
 use std::net::{SocketAddr, TcpListener, TcpStream, ToSocketAddrs};
 
 use core::mem::replace;
-use sys_util::pipe;
+use libchromeos::vsock::{self, VsockListener, VsockStream};
+use sys_util::{handle_eintr, pipe};
 
-use super::to_sys_util::{self, VsockCid, VsockStreamListener};
+use super::to_sys_util::VsockCid;
 
 const DEFAULT_PORT: u32 = 5552;
 
@@ -98,6 +99,11 @@
     Ok(Transport(Box::new(stream), Box::new(write)))
 }
 
+fn vsockstream_to_transport(stream: VsockStream) -> Result<Transport> {
+    let write = stream.try_clone().map_err(Error::Clone)?;
+    Ok(Transport(Box::new(stream), Box::new(write)))
+}
+
 /// Abstracts transport methods that accept incoming connections.
 pub trait ServerTransport {
     fn accept(&mut self) -> Result<Transport>;
@@ -127,7 +133,7 @@
 
 impl ServerTransport for IPServerTransport {
     fn accept(&mut self) -> Result<Transport> {
-        let (stream, _) = self.0.accept().map_err(Error::Accept)?;
+        let (stream, _) = handle_eintr!(self.0.accept()).map_err(Error::Accept)?;
         tcpstream_to_transport(stream)
     }
 }
@@ -149,26 +155,25 @@
 
 impl ClientTransport for IPClientTransport {
     fn connect(&mut self) -> Result<Transport> {
-        let stream = TcpStream::connect(&self.0).map_err(Error::Connect)?;
+        let stream = handle_eintr!(TcpStream::connect(&self.0)).map_err(Error::Connect)?;
         tcpstream_to_transport(stream)
     }
 }
 
 /// A transport method that listens for incoming vsock connections.
-pub struct VsockServerTransport(VsockStreamListener);
+pub struct VsockServerTransport(VsockListener);
 
 impl VsockServerTransport {
     pub fn new() -> Result<Self> {
-        let listener =
-            VsockStreamListener::new(VsockCid::Any, DEFAULT_PORT).map_err(Error::Bind)?;
+        let listener = VsockListener::bind(DEFAULT_PORT).map_err(Error::Bind)?;
         Ok(VsockServerTransport(listener))
     }
 }
 
 impl ServerTransport for VsockServerTransport {
     fn accept(&mut self) -> Result<Transport> {
-        let (stream, _) = self.0.accept().map_err(Error::Accept)?;
-        tcpstream_to_transport(stream)
+        let (stream, _) = handle_eintr!(self.0.accept()).map_err(Error::Accept)?;
+        vsockstream_to_transport(stream)
     }
 }
 
@@ -183,8 +188,12 @@
 
 impl ClientTransport for VsockClientTransport {
     fn connect(&mut self) -> Result<Transport> {
-        let stream = to_sys_util::vsock_connect(self.0, DEFAULT_PORT).map_err(Error::Connect)?;
-        tcpstream_to_transport(stream)
+        let addr = vsock::SocketAddr {
+            cid: self.0.into(),
+            port: DEFAULT_PORT,
+        };
+        let stream = handle_eintr!(VsockStream::connect(&addr)).map_err(Error::Connect)?;
+        vsockstream_to_transport(stream)
     }
 }