use std::thread; use mio::{Events, Poll, Token, Ready, PollOpt}; use mio_extras::channel::{channel, Sender, Receiver}; use crate::common::clientpool::{ClientPool, ClientAction, ClientPoolAction}; use crate::common::serverstate::{RecvServerPacket, SendServerPacket, ServerState, OnConnect}; fn recv_from_clientpool(state: &mut STATE, pool_recv: &Receiver>, pool_send: &Sender>) where STATE: ServerState, S: SendServerPacket, R: RecvServerPacket, E: std::fmt::Debug, { loop { match pool_recv.try_recv() { Ok(incoming) => { match incoming { ClientPoolAction::NewClient(client_id) => { for s in state.on_connect(client_id).into_iter() { match s { OnConnect::Cipher((in_cipher, out_cipher)) => { pool_send.send(ClientAction::EncryptionKeys(client_id, in_cipher, out_cipher)).unwrap(); } OnConnect::Packet(pkt) => { pool_send.send(ClientAction::Packet(client_id, pkt)).unwrap(); } } } }, ClientPoolAction::Packet(client_id, pkt) => { let to_send = state.handle(client_id, &pkt); match to_send { Ok(pkts) => { for p in pkts { pool_send.send(ClientAction::Packet(p.0, p.1)).unwrap(); } }, Err(err) => { // TODO: break? println!("[handler error]: {:?} {:?}", client_id, err); } } } } }, Err(_err) => { break; } } } } pub fn mainloop(mut state: STATE, port: u16) where STATE: ServerState + Send + 'static, S: SendServerPacket + std::fmt::Debug + Send + 'static, R: RecvServerPacket + std::fmt::Debug + Send + 'static, E: std::fmt::Debug, { let (pool_send, pool_recv) = channel(); //let (patch_handler_send, patch_handler_recv) = channel::>(); let (handler_send, handler_recv) = channel(); //let sender_clone = patch_handler_send.clone(); let client_thread = thread::spawn(move || { let clientpool = ClientPool::new(pool_recv, handler_send, port); clientpool.io_loop(); }); //let handler_threadpool = threadpool::ThreadPool::new(4); let handler_thread = thread::spawn(move || { let poll = Poll::new().unwrap(); poll.register(&handler_recv, Token(0), Ready::readable(), PollOpt::edge()).unwrap(); let mut events = Events::with_capacity(1024); loop { poll.poll(&mut events, None).unwrap(); for event in &events { match event.token() { Token(0) => recv_from_clientpool(&mut state, &handler_recv, &pool_send), _ => panic!() } } } }); client_thread.join().unwrap(); handler_thread.join().unwrap(); }