Overall improvements
This commit is contained in:
parent
6df9155c32
commit
9096e94f00
5 changed files with 85 additions and 85 deletions
|
|
@ -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<T>(mut args: T) -> Result<Config, Box<dyn Error>>
|
||||
where
|
||||
T: Iterator<Item = String>,
|
||||
{
|
||||
pub fn new<T: Iterator<Item = String>>(mut args: T) -> Result<Config, Box<dyn Error>> {
|
||||
let mut config = Config {
|
||||
ip_address: Ipv4Addr::new(127, 0, 0, 1),
|
||||
port: 69,
|
||||
|
|
|
|||
|
|
@ -121,15 +121,22 @@ impl Server {
|
|||
ErrorCode::FileExists => {
|
||||
let worker_options =
|
||||
parse_options(options, RequestType::Read(file_path.metadata()?.len()))?;
|
||||
let mut socket: Box<dyn Socket>;
|
||||
|
||||
if self.single_port {
|
||||
let mut socket = create_single_socket(&self.socket, to)?;
|
||||
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);
|
||||
|
||||
socket = Box::new(single_socket);
|
||||
} else {
|
||||
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)?;
|
||||
|
||||
self.clients.insert(*to, socket.sender());
|
||||
self.largest_block_size =
|
||||
max(self.largest_block_size, worker_options.block_size);
|
||||
accept_request(
|
||||
&socket,
|
||||
options,
|
||||
|
|
@ -144,26 +151,6 @@ impl Server {
|
|||
worker_options.window_size,
|
||||
);
|
||||
worker.send()
|
||||
} 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()
|
||||
}
|
||||
}
|
||||
_ => Err("Unexpected error code when checking file".into()),
|
||||
}
|
||||
|
|
@ -191,15 +178,22 @@ impl Server {
|
|||
),
|
||||
ErrorCode::FileNotFound => {
|
||||
let worker_options = parse_options(options, RequestType::Write)?;
|
||||
let mut socket: Box<dyn Socket>;
|
||||
|
||||
if self.single_port {
|
||||
let mut socket = create_single_socket(&self.socket, to)?;
|
||||
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);
|
||||
|
||||
socket = Box::new(single_socket);
|
||||
} else {
|
||||
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)?;
|
||||
|
||||
self.clients.insert(*to, 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(
|
||||
|
|
@ -210,22 +204,6 @@ impl Server {
|
|||
worker_options.window_size,
|
||||
);
|
||||
worker.receive()
|
||||
} 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()
|
||||
}
|
||||
}
|
||||
_ => Err("Unexpected error code when checking file".into()),
|
||||
}
|
||||
|
|
|
|||
|
|
@ -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<dyn Error>>;
|
||||
|
|
@ -165,6 +164,36 @@ impl ServerSocket {
|
|||
}
|
||||
}
|
||||
|
||||
impl<T: Socket + ?Sized> Socket for Box<T> {
|
||||
fn send(&self, packet: &Packet) -> Result<(), Box<dyn Error>> {
|
||||
(**self).send(packet)
|
||||
}
|
||||
|
||||
fn send_to(&self, packet: &Packet, to: &SocketAddr) -> Result<(), Box<dyn Error>> {
|
||||
(**self).send_to(packet, to)
|
||||
}
|
||||
|
||||
fn recv(&self, buf: &mut [u8]) -> Result<Packet, Box<dyn Error>> {
|
||||
(**self).recv(buf)
|
||||
}
|
||||
|
||||
fn recv_from(&self, buf: &mut [u8]) -> Result<(Packet, SocketAddr), Box<dyn Error>> {
|
||||
(**self).recv_from(buf)
|
||||
}
|
||||
|
||||
fn remote_addr(&self) -> Result<SocketAddr, Box<dyn Error>> {
|
||||
(**self).remote_addr()
|
||||
}
|
||||
|
||||
fn set_read_timeout(&mut self, dur: Duration) -> Result<(), Box<dyn Error>> {
|
||||
(**self).set_read_timeout(dur)
|
||||
}
|
||||
|
||||
fn set_write_timeout(&mut self, dur: Duration) -> Result<(), Box<dyn Error>> {
|
||||
(**self).set_write_timeout(dur)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
|
|
|||
|
|
@ -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);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -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<T>
|
||||
where
|
||||
T: Socket,
|
||||
{
|
||||
socket: T,
|
||||
pub struct Worker<T: Socket + ?Sized> {
|
||||
socket: Box<T>,
|
||||
file_name: PathBuf,
|
||||
blk_size: usize,
|
||||
timeout: Duration,
|
||||
windowsize: u16,
|
||||
}
|
||||
|
||||
impl<T> Worker<T>
|
||||
where
|
||||
T: Socket,
|
||||
{
|
||||
impl<T: Socket + ?Sized> Worker<T> {
|
||||
/// Creates a new [`Worker`] with the supplied options.
|
||||
pub fn new(
|
||||
socket: T,
|
||||
socket: Box<T>,
|
||||
file_name: PathBuf,
|
||||
blk_size: usize,
|
||||
timeout: Duration,
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue