Fix single port RRQ with options fail (#17)

This commit is contained in:
Kimmo Jyrinki 2024-03-12 11:58:35 +02:00 committed by GitHub
parent cb00acd3a4
commit d0411591f1
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 23 additions and 22 deletions

View file

@ -184,7 +184,7 @@ impl Server {
worker_options.window_size, worker_options.window_size,
self.duplicate_packets + 1, self.duplicate_packets + 1,
); );
worker.send() worker.send(!options.is_empty())
} }
_ => Err("Unexpected error code when checking file".into()), _ => Err("Unexpected error code when checking file".into()),
} }
@ -349,9 +349,6 @@ fn accept_request<T: Socket>(
) -> Result<(), Box<dyn Error>> { ) -> Result<(), Box<dyn Error>> {
if !options.is_empty() { if !options.is_empty() {
socket.send(&Packet::Oack(options.to_vec()))?; socket.send(&Packet::Oack(options.to_vec()))?;
if let RequestType::Read(_) = request_type {
check_response(socket)?;
}
} else if request_type == RequestType::Write { } else if request_type == RequestType::Write {
socket.send(&Packet::Ack(0))?; socket.send(&Packet::Ack(0))?;
} }
@ -359,19 +356,6 @@ fn accept_request<T: Socket>(
Ok(()) Ok(())
} }
fn check_response<T: Socket>(socket: &T) -> Result<(), Box<dyn Error>> {
if let Packet::Ack(received_block_number) = socket.recv()? {
if received_block_number != 0 {
socket.send(&Packet::Error {
code: ErrorCode::IllegalOperation,
msg: "invalid oack response".to_string(),
})?;
}
}
Ok(())
}
fn check_file_exists(file: &Path, directory: &PathBuf) -> ErrorCode { fn check_file_exists(file: &Path, directory: &PathBuf) -> ErrorCode {
if !validate_file_path(file, directory) { if !validate_file_path(file, directory) {
return ErrorCode::AccessViolation; return ErrorCode::AccessViolation;

View file

@ -1,4 +1,4 @@
use crate::{Packet, Socket, Window}; use crate::{ErrorCode, Packet, Socket, Window};
use std::{ use std::{
error::Error, error::Error,
fs::{self, File}, fs::{self, File},
@ -26,6 +26,7 @@ const DEFAULT_DUPLICATE_DELAY: Duration = Duration::from_millis(1);
/// // Send a file, responding to a read request. /// // Send a file, responding to a read request.
/// let socket = UdpSocket::bind("127.0.0.1:0").unwrap(); /// let socket = UdpSocket::bind("127.0.0.1:0").unwrap();
/// socket.connect(SocketAddr::from_str("127.0.0.1:12345").unwrap()).unwrap(); /// socket.connect(SocketAddr::from_str("127.0.0.1:12345").unwrap()).unwrap();
/// let has_options = false;
/// ///
/// let worker = Worker::new( /// let worker = Worker::new(
/// Box::new(socket), /// Box::new(socket),
@ -36,7 +37,7 @@ const DEFAULT_DUPLICATE_DELAY: Duration = Duration::from_millis(1);
/// 1, /// 1,
/// ); /// );
/// ///
/// worker.send().unwrap(); /// worker.send(has_options).unwrap();
/// ``` /// ```
pub struct Worker<T: Socket + ?Sized> { pub struct Worker<T: Socket + ?Sized> {
socket: Box<T>, socket: Box<T>,
@ -69,13 +70,13 @@ impl<T: Socket + ?Sized> Worker<T> {
/// Sends a file to the remote [`SocketAddr`] that has sent a read request using /// Sends a file to the remote [`SocketAddr`] that has sent a read request using
/// a random port, asynchronously. /// a random port, asynchronously.
pub fn send(self) -> Result<(), Box<dyn Error>> { pub fn send(self, check_response: bool) -> Result<(), Box<dyn Error>> {
let file_name = self.file_name.clone(); let file_name = self.file_name.clone();
let remote_addr = self.socket.remote_addr().unwrap(); let remote_addr = self.socket.remote_addr().unwrap();
thread::spawn(move || { thread::spawn(move || {
let handle_send = || -> Result<(), Box<dyn Error>> { let handle_send = || -> Result<(), Box<dyn Error>> {
self.send_file(File::open(&file_name)?)?; self.send_file(File::open(&file_name)?, check_response)?;
Ok(()) Ok(())
}; };
@ -130,10 +131,13 @@ impl<T: Socket + ?Sized> Worker<T> {
Ok(()) Ok(())
} }
fn send_file(self, file: File) -> Result<(), Box<dyn Error>> { fn send_file(self, file: File, check_response: bool) -> Result<(), Box<dyn Error>> {
let mut block_number = 1; let mut block_number = 1;
let mut window = Window::new(self.windowsize, self.blk_size, file); let mut window = Window::new(self.windowsize, self.blk_size, file);
if check_response {
self.check_response()?;
}
loop { loop {
let filled = window.fill()?; let filled = window.fill()?;
@ -251,4 +255,17 @@ impl<T: Socket + ?Sized> Worker<T> {
Ok(()) Ok(())
} }
fn check_response(&self) -> Result<(), Box<dyn Error>> {
if let Packet::Ack(received_block_number) = self.socket.recv()? {
if received_block_number != 0 {
self.socket.send(&Packet::Error {
code: ErrorCode::IllegalOperation,
msg: "invalid oack response".to_string(),
})?;
}
}
Ok(())
}
} }