diff --git a/Cargo.lock b/Cargo.lock index 87c44fa9ff..bc0ed2071e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -191,7 +191,7 @@ dependencies = [ [[package]] name = "netutils" version = "0.1.0" -source = "git+https://github.com/redox-os/netutils.git#ec1a835a9d4a95a8e41c4e994a540d298d897cd4" +source = "git+https://github.com/redox-os/netutils.git#29b8efd41d8c56b33c619db78e5b019934dbb7a3" dependencies = [ "arg_parser 0.1.0 (git+https://github.com/redox-os/arg-parser.git)", "extra 0.1.0 (git+https://github.com/redox-os/libextra.git)", @@ -328,7 +328,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] name = "smoltcp" version = "0.4.0" -source = "git+https://github.com/m-labs/smoltcp.git#b0fc1d9542ef3b8e7add3b90dcf2d6f1fc4c633e" +source = "git+https://github.com/m-labs/smoltcp.git#096ce02ac4c935c4df485a79107fb26b5897065d" dependencies = [ "byteorder 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)", diff --git a/src/smolnetd/scheme/ip.rs b/src/smolnetd/scheme/ip.rs index d48fd52f4f..4edb53b5f9 100644 --- a/src/smolnetd/scheme/ip.rs +++ b/src/smolnetd/scheme/ip.rs @@ -1,7 +1,8 @@ use super::socket::*; -use smoltcp::socket::{RawPacketBuffer, RawSocket, RawSocketBuffer, Socket, SocketHandle}; +use smoltcp::socket::{RawPacketBuffer, RawSocket, RawSocketBuffer, SocketHandle}; use smoltcp::wire::{IpProtocol, IpVersion}; +use smoltcp; use std::io::{Read, Write}; use std::str; use std::mem; @@ -93,10 +94,11 @@ impl<'a, 'b> SchemeSocket for RawSocket<'a, 'b> { } fn new_socket( + socket_set: &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, path: &str, uid: u32, _: &mut Self::SchemeDataT, - ) -> syscall::Result<(Socket<'static, 'static>, Self::DataT)> { + ) -> syscall::Result<(SocketHandle, Self::DataT)> { if uid != 0 { return Err(syscall::Error::new(syscall::EACCES)); } @@ -117,7 +119,9 @@ impl<'a, 'b> SchemeSocket for RawSocket<'a, 'b> { rx_buffer, tx_buffer, ); - Ok((ip_socket, ())) + + let socket_handle = socket_set.add(ip_socket); + Ok((socket_handle, ())) } fn close_file(&self, _: &SchemeFile, _: &mut Self::SchemeDataT) -> syscall::Result<()> { @@ -155,10 +159,10 @@ impl<'a, 'b> SchemeSocket for RawSocket<'a, 'b> { } fn dup( - &self, - _: &mut SchemeFile, - fd: usize, + _socket_set: &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, socket_handle: SocketHandle, + _file: &mut SchemeFile, + fd: usize, path: &str, _: &mut Self::SchemeDataT, ) -> syscall::Result> { diff --git a/src/smolnetd/scheme/socket.rs b/src/smolnetd/scheme/socket.rs index 586e4501a0..7d5b3ec05e 100644 --- a/src/smolnetd/scheme/socket.rs +++ b/src/smolnetd/scheme/socket.rs @@ -1,4 +1,5 @@ -use smoltcp::socket::{AsSocket, Socket, SocketHandle}; +use smoltcp::socket::{AnySocket, SocketHandle}; +use smoltcp; use std::collections::BTreeMap; use std::fs::File; use std::io::{Read, Write}; @@ -81,7 +82,7 @@ type WaitQueue = Vec; type WaitQueueMap = BTreeMap; -pub type DupResult = (SchemeFile, Option<(Socket<'static, 'static>, T::DataT)>); +pub type DupResult = (SchemeFile, Option<(SocketHandle, T::DataT)>); pub trait SchemeSocket where @@ -100,10 +101,11 @@ where fn set_setting(&mut SocketFile, Self::SettingT, &[u8]) -> syscall::Result; fn new_socket( + &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, &str, u32, &mut Self::SchemeDataT, - ) -> syscall::Result<(Socket<'static, 'static>, Self::DataT)>; + ) -> syscall::Result<(SocketHandle, Self::DataT)>; fn close_file(&self, &SchemeFile, &mut Self::SchemeDataT) -> syscall::Result<()>; fn write_buf(&mut self, &mut SocketFile, buf: &[u8]) -> syscall::Result; @@ -112,10 +114,10 @@ where fn fpath(&self, &SchemeFile, &mut [u8]) -> syscall::Result; fn dup( - &self, + &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, + SocketHandle, &mut SchemeFile, usize, - SocketHandle, &str, &mut Self::SchemeDataT, ) -> syscall::Result>; @@ -123,8 +125,7 @@ where pub struct SocketScheme where - SocketT: SchemeSocket, - Socket<'static, 'static>: AsSocket, + SocketT: SchemeSocket + AnySocket<'static, 'static>, { next_fd: usize, fds: BTreeMap>, @@ -137,8 +138,7 @@ where impl SocketScheme where - SocketT: SchemeSocket, - Socket<'static, 'static>: AsSocket, + SocketT: SchemeSocket + AnySocket<'static, 'static>, { pub fn new(socket_set: SocketSet, scheme_file: File) -> SocketScheme { SocketScheme { @@ -180,7 +180,7 @@ where }) = *handle { let mut socket_set = self.socket_set.borrow_mut(); - let socket: &mut SocketT = socket_set.get_mut(socket_handle).as_socket(); + let socket = socket_set.get::(socket_handle); if events & syscall::EVENT_READ == syscall::EVENT_READ && socket.can_recv() { post_fevent(&mut self.scheme_file, fd, syscall::EVENT_READ, 1)?; @@ -373,16 +373,19 @@ where impl syscall::SchemeMut for SocketScheme where - SocketT: SchemeSocket, - Socket<'static, 'static>: AsSocket, + SocketT: SchemeSocket + AnySocket<'static, 'static>, { fn open(&mut self, url: &[u8], flags: usize, uid: u32, _gid: u32) -> syscall::Result { let path = str::from_utf8(url).or_else(|_| Err(syscall::Error::new(syscall::EINVAL)))?; trace!("open {}", path); - let (socket, data) = SocketT::new_socket(path, uid, &mut self.scheme_data)?; + let (socket_handle, data) = SocketT::new_socket( + &mut self.socket_set.borrow_mut(), + path, + uid, + &mut self.scheme_data, + )?; - let socket_handle = self.socket_set.borrow_mut().add(socket); let id = self.next_fd; self.fds.insert( @@ -411,7 +414,7 @@ where let scheme_file = self.fds.remove(&fd); let mut socket_set = self.socket_set.borrow_mut(); if let Some(scheme_file) = scheme_file { - let socket: &mut SocketT = socket_set.get_mut(socket_handle).as_socket(); + let socket = socket_set.get::(socket_handle); socket.close_file(&scheme_file, &mut self.scheme_data)?; } let remove_wq = @@ -447,9 +450,9 @@ where } SchemeFile::Socket(ref mut handle) => { let mut socket_set = self.socket_set.borrow_mut(); - let socket: &mut SocketT = socket_set.get_mut(handle.socket_handle).as_socket(); + let mut socket = socket_set.get::(handle.socket_handle); - return ::write_buf(socket, handle, buf); + return ::write_buf(&mut socket, handle, buf); } } }; @@ -467,8 +470,8 @@ where } SchemeFile::Socket(ref mut handle) => { let mut socket_set = self.socket_set.borrow_mut(); - let socket: &mut SocketT = socket_set.get_mut(handle.socket_handle).as_socket(); - return ::read_buf(socket, handle, buf); + let mut socket = socket_set.get::(handle.socket_handle); + return ::read_buf(&mut socket, handle, buf); } } }; @@ -485,15 +488,17 @@ where let socket_handle = handle.socket_handle(); - let (new_handle, update_with) = { - let mut socket_set = self.socket_set.borrow_mut(); - let socket: &mut SocketT = socket_set.get_mut(handle.socket_handle()).as_socket(); - socket.dup(handle, fd, socket_handle, path, &mut self.scheme_data)? - }; + let (new_handle, update_with) = SocketT::dup( + &mut self.socket_set.borrow_mut(), + socket_handle, + handle, + fd, + path, + &mut self.scheme_data, + )?; - if let Some((socket, data)) = update_with { + if let Some((socket_handle, data)) = update_with { if let SchemeFile::Socket(ref mut handle) = *handle { - let socket_handle = self.socket_set.borrow_mut().add(socket); trace!("Updating {} to a new socket handle {:?}", fd, socket_handle); Self::move_handle_to_new_socket_handle( &mut self.wait_queue_map, @@ -549,7 +554,7 @@ where .ok_or_else(|| syscall::Error::new(syscall::EBADF))?; let mut socket_set = self.socket_set.borrow_mut(); - let socket: &mut SocketT = socket_set.get_mut(handle.socket_handle()).as_socket(); + let socket = socket_set.get::(handle.socket_handle()); socket.fpath(handle, buf) } diff --git a/src/smolnetd/scheme/tcp.rs b/src/smolnetd/scheme/tcp.rs index 0889ac7de9..46e6de4173 100644 --- a/src/smolnetd/scheme/tcp.rs +++ b/src/smolnetd/scheme/tcp.rs @@ -1,7 +1,8 @@ use super::socket::*; -use smoltcp::socket::{AsSocket, Socket, SocketHandle, TcpSocket, TcpSocketBuffer}; +use smoltcp::socket::{SocketHandle, TcpSocket, TcpSocketBuffer}; use smoltcp::wire::{IpAddress, IpEndpoint, Ipv4Address}; +use smoltcp; use std::io::{Read, Write}; use std::str::FromStr; use std::str; @@ -99,10 +100,11 @@ impl<'a> SchemeSocket for TcpSocket<'a> { } fn new_socket( + socket_set: &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, path: &str, uid: u32, port_set: &mut Self::SchemeDataT, - ) -> syscall::Result<(Socket<'static, 'static>, Self::DataT)> { + ) -> syscall::Result<(SocketHandle, Self::DataT)> { trace!("TCP open {}", path); let mut parts = path.split('/'); let remote_endpoint = parse_endpoint(parts.next().unwrap_or("")); @@ -116,7 +118,7 @@ impl<'a> SchemeSocket for TcpSocket<'a> { let tx_packets = vec![0; 65_535]; let rx_buffer = TcpSocketBuffer::new(rx_packets); let tx_buffer = TcpSocketBuffer::new(tx_packets); - let mut socket = TcpSocket::new(rx_buffer, tx_buffer); + let socket = TcpSocket::new(rx_buffer, tx_buffer); if local_endpoint.port == 0 { local_endpoint.port = port_set @@ -126,23 +128,23 @@ impl<'a> SchemeSocket for TcpSocket<'a> { return Err(syscall::Error::new(syscall::EADDRINUSE)); } - { - let tcp_socket: &mut TcpSocket = socket.as_socket(); + let socket_handle = socket_set.add(socket); - if remote_endpoint.is_specified() { - trace!("Connecting tcp {} {}", local_endpoint, remote_endpoint); - tcp_socket - .connect(remote_endpoint, local_endpoint) - .expect("Can't connect tcp socket "); - } else { - trace!("Listening tcp {}", local_endpoint); - tcp_socket - .listen(local_endpoint) - .expect("Can't listen on local endpoint"); - } + let mut tcp_socket = socket_set.get::(socket_handle); + + if remote_endpoint.is_specified() { + trace!("Connecting tcp {} {}", local_endpoint, remote_endpoint); + tcp_socket + .connect(remote_endpoint, local_endpoint) + .expect("Can't connect tcp socket "); + } else { + trace!("Listening tcp {}", local_endpoint); + tcp_socket + .listen(local_endpoint) + .expect("Can't listen on local endpoint"); } - Ok((socket, ())) + Ok((socket_handle, ())) } fn close_file( @@ -191,13 +193,18 @@ impl<'a> SchemeSocket for TcpSocket<'a> { } fn dup( - &self, + socket_set: &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, + socket_handle: SocketHandle, file: &mut SchemeFile, fd: usize, - socket_handle: SocketHandle, path: &str, port_set: &mut Self::SchemeDataT, ) -> syscall::Result> { + let (is_active, local_endpoint) = { + let socket = socket_set.get::(socket_handle); + (socket.is_active(), socket.local_endpoint()) + }; + let handle = match path { "ttl" => SchemeFile::Setting(SettingFile { socket_handle, @@ -215,7 +222,7 @@ impl<'a> SchemeSocket for TcpSocket<'a> { setting: Setting::WriteTimeout, }), "listen" => if let SchemeFile::Socket(ref tcp_handle) = *file { - if !self.is_active() { + if !is_active { return Err(syscall::Error::new(syscall::EWOULDBLOCK)); } trace!("TCP creating new listening socket"); @@ -225,15 +232,16 @@ impl<'a> SchemeSocket for TcpSocket<'a> { let tx_packets = vec![0; 65_535]; let rx_buffer = TcpSocketBuffer::new(rx_packets); let tx_buffer = TcpSocketBuffer::new(tx_packets); - let mut socket = TcpSocket::new(rx_buffer, tx_buffer); + let socket = TcpSocket::new(rx_buffer, tx_buffer); + let new_socket_handle = socket_set.add(socket); { - let tcp_socket: &mut TcpSocket = socket.as_socket(); + let mut tcp_socket = socket_set.get::(new_socket_handle); tcp_socket - .listen(self.local_endpoint()) + .listen(local_endpoint) .expect("Can't listen on local endpoint"); } - port_set.acquire_port(self.local_endpoint().port); - return Ok((new_handle, Some((socket, ())))); + port_set.acquire_port(local_endpoint.port); + return Ok((new_handle, Some((new_socket_handle, ())))); } else { return Err(syscall::Error::new(syscall::EBADF)); }, @@ -248,7 +256,7 @@ impl<'a> SchemeSocket for TcpSocket<'a> { }; if let SchemeFile::Socket(_) = handle { - port_set.acquire_port(self.local_endpoint().port); + port_set.acquire_port(local_endpoint.port); } Ok((handle, None)) diff --git a/src/smolnetd/scheme/udp.rs b/src/smolnetd/scheme/udp.rs index 93203e4bca..9641984b7d 100644 --- a/src/smolnetd/scheme/udp.rs +++ b/src/smolnetd/scheme/udp.rs @@ -1,7 +1,8 @@ use super::socket::*; -use smoltcp::socket::{AsSocket, Socket, SocketHandle, UdpPacketBuffer, UdpSocket, UdpSocketBuffer}; +use smoltcp::socket::{SocketHandle, UdpPacketBuffer, UdpSocket, UdpSocketBuffer}; use smoltcp::wire::{IpAddress, IpEndpoint, Ipv4Address}; +use smoltcp; use std::io::{Read, Write}; use std::str::FromStr; use std::str; @@ -100,10 +101,11 @@ impl<'a, 'b> SchemeSocket for UdpSocket<'a, 'b> { } fn new_socket( + socket_set: &mut smoltcp::socket::SocketSet<'static, 'static, 'static>, path: &str, uid: u32, port_set: &mut Self::SchemeDataT, - ) -> syscall::Result<(Socket<'static, 'static>, Self::DataT)> { + ) -> syscall::Result<(SocketHandle, Self::DataT)> { let mut parts = path.split('/'); let remote_endpoint = parse_endpoint(parts.next().unwrap_or("")); let mut local_endpoint = parse_endpoint(parts.next().unwrap_or("")); @@ -120,7 +122,7 @@ impl<'a, 'b> SchemeSocket for UdpSocket<'a, 'b> { } let rx_buffer = UdpSocketBuffer::new(rx_packets); let tx_buffer = UdpSocketBuffer::new(tx_packets); - let mut udp_socket = UdpSocket::new(rx_buffer, tx_buffer); + let udp_socket = UdpSocket::new(rx_buffer, tx_buffer); if local_endpoint.port == 0 { local_endpoint.port = port_set @@ -130,14 +132,14 @@ impl<'a, 'b> SchemeSocket for UdpSocket<'a, 'b> { return Err(syscall::Error::new(syscall::EADDRINUSE)); } - { - let udp_socket: &mut UdpSocket = udp_socket.as_socket(); - udp_socket - .bind(local_endpoint) - .expect("Can't bind udp socket to local endpoint"); - } + let socket_handle = socket_set.add(udp_socket); - Ok((udp_socket, remote_endpoint)) + let mut udp_socket = socket_set.get::(socket_handle); + udp_socket + .bind(local_endpoint) + .expect("Can't bind udp socket to local endpoint"); + + Ok((socket_handle, remote_endpoint)) } fn close_file( @@ -185,10 +187,10 @@ impl<'a, 'b> SchemeSocket for UdpSocket<'a, 'b> { } fn dup( - &self, + socket_set: &mut smoltcp::socket::SocketSet, + socket_handle: SocketHandle, file: &mut SchemeFile, fd: usize, - socket_handle: SocketHandle, path: &str, port_set: &mut Self::SchemeDataT, ) -> syscall::Result> { @@ -224,8 +226,13 @@ impl<'a, 'b> SchemeSocket for UdpSocket<'a, 'b> { } }; + let endpoint = { + let socket = socket_set.get::(socket_handle); + socket.endpoint() + }; + if let SchemeFile::Socket(_) = handle { - port_set.acquire_port(self.endpoint().port); + port_set.acquire_port(endpoint.port); } Ok((handle, None))