From 9096e94f001e5c8d881dbc04b593b15d7267eb34 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Altu=C4=9F=20Bakan?= Date: Fri, 12 May 2023 07:59:53 +0000 Subject: [PATCH] Overall improvements --- src/config.rs | 5 +-- src/server.rs | 106 ++++++++++++++++++++------------------------------ src/socket.rs | 35 +++++++++++++++-- src/window.rs | 8 ++-- src/worker.rs | 16 +++----- 5 files changed, 85 insertions(+), 85 deletions(-) diff --git a/src/config.rs b/src/config.rs index 17a22e2..b4ac71a 100644 --- a/src/config.rs +++ b/src/config.rs @@ -32,10 +32,7 @@ pub struct Config { impl Config { /// Creates a new configuration by parsing the supplied arguments. It is /// intended for use with [`env::args()`]. - pub fn new(mut args: T) -> Result> - where - T: Iterator, - { + pub fn new>(mut args: T) -> Result> { let mut config = Config { ip_address: Ipv4Addr::new(127, 0, 0, 1), port: 69, diff --git a/src/server.rs b/src/server.rs index e793eb8..df910cf 100644 --- a/src/server.rs +++ b/src/server.rs @@ -121,49 +121,36 @@ impl Server { ErrorCode::FileExists => { let worker_options = parse_options(options, RequestType::Read(file_path.metadata()?.len()))?; + let mut socket: Box; if self.single_port { - let mut socket = create_single_socket(&self.socket, to)?; - socket.set_read_timeout(worker_options.timeout)?; - socket.set_write_timeout(worker_options.timeout)?; - - self.clients.insert(*to, socket.sender()); + let single_socket = create_single_socket(&self.socket, to)?; + self.clients.insert(*to, single_socket.sender()); self.largest_block_size = max(self.largest_block_size, worker_options.block_size); - accept_request( - &socket, - options, - RequestType::Read(file_path.metadata()?.len()), - )?; - let worker = Worker::new( - socket, - file_path.clone(), - worker_options.block_size, - worker_options.timeout, - worker_options.window_size, - ); - worker.send() + socket = Box::new(single_socket); } else { - let socket = create_multi_socket(&self.socket.local_addr()?, to)?; - socket.set_read_timeout(Some(worker_options.timeout))?; - socket.set_write_timeout(Some(worker_options.timeout))?; - - accept_request( - &socket, - options, - RequestType::Read(file_path.metadata()?.len()), - )?; - - let worker = Worker::new( - socket, - file_path.clone(), - worker_options.block_size, - worker_options.timeout, - worker_options.window_size, - ); - worker.send() + socket = Box::new(create_multi_socket(&self.socket.local_addr()?, to)?); } + + socket.set_read_timeout(worker_options.timeout)?; + socket.set_write_timeout(worker_options.timeout)?; + + accept_request( + &socket, + options, + RequestType::Read(file_path.metadata()?.len()), + )?; + + let worker = Worker::new( + socket, + file_path.clone(), + worker_options.block_size, + worker_options.timeout, + worker_options.window_size, + ); + worker.send() } _ => Err("Unexpected error code when checking file".into()), } @@ -191,41 +178,32 @@ impl Server { ), ErrorCode::FileNotFound => { let worker_options = parse_options(options, RequestType::Write)?; + let mut socket: Box; if self.single_port { - let mut socket = create_single_socket(&self.socket, to)?; - socket.set_read_timeout(worker_options.timeout)?; - socket.set_write_timeout(worker_options.timeout)?; - - self.clients.insert(*to, socket.sender()); + let single_socket = create_single_socket(&self.socket, to)?; + self.clients.insert(*to, single_socket.sender()); self.largest_block_size = max(self.largest_block_size, worker_options.block_size); - accept_request(&socket, options, RequestType::Write)?; - let worker = Worker::new( - socket, - file_path.clone(), - worker_options.block_size, - worker_options.timeout, - worker_options.window_size, - ); - worker.receive() + socket = Box::new(single_socket); } else { - let socket = create_multi_socket(&self.socket.local_addr()?, to)?; - socket.set_read_timeout(Some(worker_options.timeout))?; - socket.set_write_timeout(Some(worker_options.timeout))?; - - accept_request(&socket, options, RequestType::Write)?; - - let worker = Worker::new( - socket, - file_path.clone(), - worker_options.block_size, - worker_options.timeout, - worker_options.window_size, - ); - worker.receive() + socket = Box::new(create_multi_socket(&self.socket.local_addr()?, to)?); } + + socket.set_read_timeout(worker_options.timeout)?; + socket.set_write_timeout(worker_options.timeout)?; + + accept_request(&socket, options, RequestType::Write)?; + + let worker = Worker::new( + socket, + file_path.clone(), + worker_options.block_size, + worker_options.timeout, + worker_options.window_size, + ); + worker.receive() } _ => Err("Unexpected error code when checking file".into()), } diff --git a/src/socket.rs b/src/socket.rs index 9638d73..00b853e 100644 --- a/src/socket.rs +++ b/src/socket.rs @@ -12,9 +12,8 @@ use crate::Packet; const DEFAULT_TIMEOUT: Duration = Duration::from_secs(5); -/// Socket `trait` is used for easy message transmission of common TFTP -/// message types. This `trait` is implemented for [`UdpSocket`] and used -/// for abstraction of single socket communication. +/// Socket `trait` is used to allow building custom sockets to be used for +/// TFTP communication. pub trait Socket: Send + Sync + 'static { /// Sends a [`Packet`] to the socket's connected remote [`Socket`]. fn send(&self, packet: &Packet) -> Result<(), Box>; @@ -165,6 +164,36 @@ impl ServerSocket { } } +impl Socket for Box { + fn send(&self, packet: &Packet) -> Result<(), Box> { + (**self).send(packet) + } + + fn send_to(&self, packet: &Packet, to: &SocketAddr) -> Result<(), Box> { + (**self).send_to(packet, to) + } + + fn recv(&self, buf: &mut [u8]) -> Result> { + (**self).recv(buf) + } + + fn recv_from(&self, buf: &mut [u8]) -> Result<(Packet, SocketAddr), Box> { + (**self).recv_from(buf) + } + + fn remote_addr(&self) -> Result> { + (**self).remote_addr() + } + + fn set_read_timeout(&mut self, dur: Duration) -> Result<(), Box> { + (**self).set_read_timeout(dur) + } + + fn set_write_timeout(&mut self, dur: Duration) -> Result<(), Box> { + (**self).set_write_timeout(dur) + } +} + #[cfg(test)] mod tests { use super::*; diff --git a/src/window.rs b/src/window.rs index 933b059..eb07e28 100644 --- a/src/window.rs +++ b/src/window.rs @@ -5,9 +5,9 @@ use std::{ io::{Read, Write}, }; -/// Window `struct` is used to store chunks of data from a file. -/// It is used to store the data that is being sent or received for -/// Windowsize option. +/// Window `struct` is used to store chunks of data from a file. It is +/// used to help store the data that is being sent or received for the +/// [RFC 7440](https://www.rfc-editor.org/rfc/rfc7440) Windowsize option. /// /// # Example /// ```rust @@ -206,8 +206,10 @@ mod tests { .unwrap() } + #[allow(unused_must_use)] fn clean(file_name: &str) { let file_name = DIR_NAME.to_string() + "/" + file_name; fs::remove_file(file_name).unwrap(); + fs::remove_dir(DIR_NAME); } } diff --git a/src/worker.rs b/src/worker.rs index ff795d3..36e0d03 100644 --- a/src/worker.rs +++ b/src/worker.rs @@ -28,7 +28,7 @@ const TIMEOUT_BUFFER: Duration = Duration::from_secs(1); /// socket.connect(SocketAddr::from_str("127.0.0.1:12345").unwrap()).unwrap(); /// /// let worker = Worker::new( -/// socket, +/// Box::new(socket), /// PathBuf::from_str("Cargo.toml").unwrap(), /// 512, /// Duration::from_secs(1), @@ -37,24 +37,18 @@ const TIMEOUT_BUFFER: Duration = Duration::from_secs(1); /// /// worker.send().unwrap(); /// ``` -pub struct Worker -where - T: Socket, -{ - socket: T, +pub struct Worker { + socket: Box, file_name: PathBuf, blk_size: usize, timeout: Duration, windowsize: u16, } -impl Worker -where - T: Socket, -{ +impl Worker { /// Creates a new [`Worker`] with the supplied options. pub fn new( - socket: T, + socket: Box, file_name: PathBuf, blk_size: usize, timeout: Duration,