这是我的代码:
use std::net; use std::thread; extern crate argparse; use argparse::{ArgumentParser,StoreTrue,Store}; fn scan_port(host: &str,port: u16) -> bool { let host = host.to_string(); let port = port; let t = thread::spawn(move || net::TcpStream::connect((host.as_str(),port)).is_ok()); t.join().unwrap() }
如果连接未在N秒内完成,如何创建线程将被终止或终止的情况?
所有这一切的原因是Rust无法设置套接字连接超时,因此我无法确保程序不会卡住.
解决方法
正如@Shepmaster所说:终止线程是个坏主意.
你可以做的是给线程一个Sender
,如果它已成功打开一个连接(甚至可能通过发送你的句柄)它应该通知你.然后你可以让你的主线程sleep
等待你想要的时间.当你的线程被唤醒时,它会从线程中检查其对应的Receiver
以查找生命迹象.如果线程没有回答,只需release it into the wild by dropping the JoinHandle
和接收器.它不像消耗cpu时间(它被阻止),而且它不会消耗太多内存.如果它解锁,它将检测到发送者没有连接并且可以关闭.
当然你不应该有这些开放线程的bazillions,因为它们仍然使用资源(内存和系统线程句柄),但在正常的系统上,这不是一个问题.
例:
use std::net; use std::thread; use std::sync::mpsc; fn scan_port(host: &str,port: u16) -> bool { let host = host.to_string(); let port = port; let (sender,receiver) = mpsc::channel(); let t = thread::spawn(move || { match sender.send(net::TcpStream::connect((host.as_str(),port))) { Ok(()) => {},// everything good Err(_) => {},// we have been released,don't panic } }); thread::sleep(std::time::Duration::new(5,0)); match receiver.try_recv() { Ok(Ok(handle)) => true,// we have a connection Ok(Err(_)) => false,// connecting Failed Err(mpsc::TryRecvError::Empty) => { drop(receiver); drop(t); // connecting took more than 5 seconds false },Err(mpsc::TryRecvError::Disconnected) => unreachable!(),} }