Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- use std::thread::spawn;
- use std::net::{TcpListener, TcpStream};
- use std::time::Duration;
- use std::sync::{Mutex, Arc};
- use std::io::ErrorKind;
- use std::io::{Read, Write};
- enum WriteType {
- Encode,
- Decode
- }
- fn main() {
- let listener = TcpListener::bind("127.0.0.1:2001").unwrap();
- for stream in listener.incoming() {
- let stream = stream.unwrap();
- stream.set_nonblocking(true).unwrap();
- println!("Connection established!");
- spawn(|| {
- handle_stream(stream);
- });
- }
- }
- fn handle_stream(mut browser: TcpStream) {
- let addr = "77.82.230.220:90".parse().unwrap();
- let timeout = Duration::from_secs(15);
- let mut server = TcpStream::connect_timeout(&addr, timeout)
- .expect("connection timed out");
- server.set_nonblocking(true);
- let server_ptr = &mut server;
- let browser_ptr = &mut browser;
- let server_mutex = Arc::new(Mutex::new(server_ptr));
- let browser_mutex = Arc::new(Mutex::new(browser_ptr));
- let server_clone = Arc::clone(&server_mutex);
- let browser_clone = Arc::clone(&browser_mutex);
- let handle1 = copy(&server_clone, &browser_clone, WriteType::Encode);
- let handle2 = copy(&browser_clone, &server_clone, WriteType::Decode);
- handle1.join();
- handle2.join();
- }
- fn encode(data: &[u8]) -> Vec<u8> {
- let mut retval: Vec<u8>;
- for t in data {
- let byte = *t;
- let d = if byte < 12u8 { byte + 244u8 } else { byte - 12u8 };
- retval.push(d);
- }
- retval
- }
- fn decode(data: &mut [u8]) -> Vec<u8> {
- let mut retval: Vec<u8>;
- for t in data {
- let byte = *t;
- let d = if byte > 243u8 { byte - 244u8 } else { byte + 12u8 };
- retval.push(d);
- }
- retval
- }
- fn copy(from: &Arc<Mutex<&mut TcpStream>>,
- to: &Arc<Mutex<&mut TcpStream>>,
- write_type: WriteType) -> std::thread::JoinHandle<()> {
- spawn(move || {
- let mut buf = [0u8;4096];
- loop {
- let mut count = 0;
- {
- let mut from_guard = from.lock().unwrap();
- match from_guard.read(&mut buf) {
- Ok(c) => { count = c },
- Err(ref e) if e.kind() == ErrorKind::WouldBlock => { },
- Err(_) => { break }
- };
- }
- if count > 0 {
- let result = match write_type {
- WriteType::Encode => encode(&mut buf[0..count]),
- WriteType::Decode => decode(&mut buf[0..count])
- };
- let mut to_guard = to.lock().unwrap();
- to_guard.write(&result).unwrap();
- to_guard.flush();
- }
- }
- })
- }
Add Comment
Please, Sign In to add comment