Fixed a few small errors

This commit is contained in:
Arlo Filley 2023-11-21 10:24:09 +00:00
parent 587b2c6bdc
commit 92f477f901
3 changed files with 260 additions and 206 deletions

1
.gitignore vendored
View File

@ -5,3 +5,4 @@ Cargo.lock
/process /process
/log /log
.DS_Store .DS_Store
/downloads

View File

@ -94,33 +94,36 @@ async fn main() {
let num_pieces = torrent.info.pieces.len() / 20; let num_pieces = torrent.info.pieces.len() / 20;
let mut peer = match Peer::create_connection(peers[0]).await {
None => { return },
Some(peer) => peer
};
peer.handshake(&torrent).await;
peer.keep_alive_until_unchoke().await;
info!("Successfully Created Connection with peer: {}", peer.peer_id);
println!("{}", peers.len()); println!("{}", peers.len());
let mut len = 0; let mut len = 0;
let mut i = 0;
let t = torrent.clone();
for index in 0..num_pieces { let (sender, mut reciever) = Peer::test(peers[0], torrent).await;
let piece= peer.request_piece(
index as u32, torrent.info.piece_length as u32,
&mut len, torrent.get_total_length() as u32
).await;
if torrent.check_piece(&piece, index as u32) { loop {
files.write_piece(piece).await; let _ = sender.send(peer::ControlMessage::DownloadPiece(i, t.info.piece_length as u32, len, t.get_total_length() as u32));
reciever.resubscribe();
let a = reciever.recv().await.unwrap();
println!("2 {a:?}");
let peer::ControlMessage::DownloadedPiece(b) = a else {
continue;
};
if t.check_piece(&b, i) {
files.write_piece(b).await;
} else { } else {
break break
} }
} }
peer.disconnect().await; //peer.disconnect().await;
info!("Successfully completed download"); info!("Successfully completed download");

View File

@ -8,11 +8,12 @@ use crate::{
}; };
// External imports // External imports
use log::{ debug, error }; use log::{ debug, error, info };
use std::net::{SocketAddr, SocketAddrV4}; use std::{net::{SocketAddr, SocketAddrV4, Ipv4Addr}, sync::mpsc::Sender};
use tokio::{ use tokio::{
io::{ AsyncReadExt, AsyncWriteExt }, io::{ AsyncReadExt, AsyncWriteExt, Ready },
net::TcpStream net::TcpStream, sync::{oneshot, broadcast}, spawn,
sync::mpsc
}; };
/// Structure to abstract interaction with a peer. /// Structure to abstract interaction with a peer.
@ -20,11 +21,11 @@ pub struct Peer {
/// The `TcpStream` that is used to communicate with the peeer /// The `TcpStream` that is used to communicate with the peeer
connection_stream: TcpStream, connection_stream: TcpStream,
/// The `SocketAddr` of the peer /// The `SocketAddr` of the peer
pub socket_addr: SocketAddrV4, socket_addr: SocketAddrV4,
/// The id of the peer /// The id of the peer
pub peer_id: String, pub peer_id: String,
/// Whether the peer is choking the client /// Whether the peer is choking the client
pub choking: bool, choking: bool,
} }
impl Peer { impl Peer {
@ -52,13 +53,62 @@ impl Peer {
choking: true, choking: true,
}) })
} }
}
#[derive(Clone, Debug)]
pub enum ControlMessage {
DownloadPiece(u32, u32, u32, u32),
DownloadedPiece(Vec<u8>)
}
impl Peer {
pub async fn test(address: SocketAddrV4, torrent: Torrent) -> (broadcast::Sender<ControlMessage>, broadcast::Receiver<ControlMessage>) {
let (sender, mut receiver) = broadcast::channel::<ControlMessage>(16);
let sx1 = sender.clone();
let rx1 = receiver.resubscribe();
let t = torrent.clone();
spawn(async move {
let mut peer = match Peer::create_connection(address).await {
None => { return },
Some(peer) => peer
};
peer.handshake(&torrent).await;
peer.keep_alive_until_unchoke().await;
info!("Successfully Created Connection with peer: {}", peer.peer_id);
loop {
if receiver.is_empty() {
continue
} else {
let Ok(m) = receiver.recv().await else {
continue;
};
println!("{m:#?}");
match m {
ControlMessage::DownloadPiece(a, b, mut c, d) => {
let buf = peer.request_piece(a, b, &mut c, d).await;
let _ = sender.send(ControlMessage::DownloadedPiece(buf));
}
_ => ()
}
}
}
});
(sx1, rx1)
}
/// Sends a handshake message to the peer, the first step in the peer wire messaging protocol. /// Sends a handshake message to the peer, the first step in the peer wire messaging protocol.
/// ///
/// # Arguments /// # Arguments
/// ///
/// * `torrent` - The `Torrent` instance associated with the peer. /// * `torrent` - The `Torrent` instance associated with the peer.
pub async fn handshake(&mut self, torrent: &Torrent) { async fn handshake(&mut self, torrent: &Torrent) {
let mut buf = vec![0; 1024]; let mut buf = vec![0; 1024];
let handshake_message = Handshake::new(&torrent.get_info_hash()).unwrap(); let handshake_message = Handshake::new(&torrent.get_info_hash()).unwrap();
@ -84,7 +134,7 @@ impl Peer {
} }
/// Keeps the connection alive and sends interested messages until the peer unchokes /// Keeps the connection alive and sends interested messages until the peer unchokes
pub async fn keep_alive_until_unchoke(&mut self) { async fn keep_alive_until_unchoke(&mut self) {
loop { loop {
let message = self.read_message().await; let message = self.read_message().await;
@ -107,7 +157,7 @@ impl Peer {
} }
/// Sends a message to the peer and waits for a response, which it returns /// Sends a message to the peer and waits for a response, which it returns
pub async fn send_message(&mut self, message: Message) -> Message { async fn send_message(&mut self, message: Message) -> Message {
let mut buf = vec![0; 16_397]; let mut buf = vec![0; 16_397];
self.connection_stream.writable().await.unwrap(); self.connection_stream.writable().await.unwrap();
@ -120,7 +170,7 @@ impl Peer {
} }
/// Sends a message to the peer and waits for a response, which it returns /// Sends a message to the peer and waits for a response, which it returns
pub async fn send_message_exact_size_response(&mut self, message: Message, size: usize) -> Message { async fn send_message_exact_size_response(&mut self, message: Message, size: usize) -> Message {
let mut buf = vec![0; size]; let mut buf = vec![0; size];
self.connection_stream.writable().await.unwrap(); self.connection_stream.writable().await.unwrap();
@ -133,13 +183,13 @@ impl Peer {
} }
/// Sends a message but doesn't wait for a response /// Sends a message but doesn't wait for a response
pub async fn send_message_no_response(&mut self, message: Message) { async fn send_message_no_response(&mut self, message: Message) {
self.connection_stream.writable().await.unwrap(); self.connection_stream.writable().await.unwrap();
self.connection_stream.write_all(&message.to_buffer()).await.unwrap(); self.connection_stream.write_all(&message.to_buffer()).await.unwrap();
} }
/// reads a message from the peer /// reads a message from the peer
pub async fn read_message(&mut self) -> Message { async fn read_message(&mut self) -> Message {
let mut buf = vec![0; 16_397]; let mut buf = vec![0; 16_397];
self.connection_stream.readable().await.unwrap(); self.connection_stream.readable().await.unwrap();
@ -149,7 +199,7 @@ impl Peer {
} }
/// Shutsdown the connection stream /// Shutsdown the connection stream
pub async fn disconnect(&mut self) { async fn disconnect(&mut self) {
match self.connection_stream.shutdown().await { match self.connection_stream.shutdown().await {
Err(err) => { Err(err) => {
error!("Error disconnecting from {}: {}", self.socket_addr, err); error!("Error disconnecting from {}: {}", self.socket_addr, err);