Compare commits

..
13 Commits
Author SHA1 Message Date
lubeilin 858ca9bbe7 去除udp通道的arc包装 2023-12-30 22:15:48 +08:00
lubeilin cbc4a7378c 优化tcp通道 2023-12-30 21:39:53 +08:00
lubeilin ee34f525e6 nat地址判断 2023-12-30 13:07:54 +08:00
lubeilin 698e2531e8 增加参数校验 2023-12-30 12:00:47 +08:00
lubeilin 16f833ec72 优化延迟优先参数 2023-12-28 23:18:57 +08:00
lubeilin 94d6caef7e 修复连接tcp地址的问题 2023-12-26 22:27:16 +08:00
lubeilin 364012f9dd fmt 2023-12-26 21:47:01 +08:00
lubeilin cf4b1f418f 忽略地址校验 2023-12-26 21:46:41 +08:00
lubeilin c6465977ef 将ipv4转换成ipv6 2023-12-26 21:46:23 +08:00
lubeilin c577e6381f 将ipv4转换成ipv6 2023-12-25 23:06:47 +08:00
lubeilin 134e31f563 fmt 2023-12-24 13:42:41 +08:00
lubeilin 0580b89f48 升级版本号 2023-12-24 12:22:34 +08:00
lubeilin 37080af275 支持ipv6服务端 2023-12-24 12:00:44 +08:00
17 changed files with 213 additions and 266 deletions
+1 -1
View File
@@ -1,6 +1,6 @@
[package] [package]
name = "common" name = "common"
version = "1.2.7" version = "1.2.8"
edition = "2021" edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+1 -1
View File
@@ -1,6 +1,6 @@
[package] [package]
name = "vnt-cli" name = "vnt-cli"
version = "1.2.7" version = "1.2.8"
edition = "2021" edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+2 -1
View File
@@ -158,7 +158,8 @@ pub fn read_config(file_path: &str) -> io::Result<(Config, bool)> {
punch_model, punch_model,
file_conf.port, file_conf.port,
file_conf.first_latency, file_conf.first_latency,
); )
.unwrap();
Ok((config, file_conf.cmd)) Ok((config, file_conf.cmd))
} }
+2 -1
View File
@@ -288,7 +288,8 @@ fn main() {
punch_model, punch_model,
port, port,
first_latency, first_latency,
); )
.unwrap();
(config, cmd) (config, cmd)
}; };
println!("version {}", vnt::VNT_VERSION); println!("version {}", vnt::VNT_VERSION);
+1 -1
View File
@@ -1,6 +1,6 @@
[package] [package]
name = "vnt-jni" name = "vnt-jni"
version = "1.2.7" version = "1.2.8"
edition = "2021" edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+12 -2
View File
@@ -130,7 +130,7 @@ fn new_sync(env: &mut JNIEnv, config: JObject) -> Result<VntUtilSync, Error> {
for addr in stun_server_str.split(",") { for addr in stun_server_str.split(",") {
stun_server.push(addr.trim().to_string()); stun_server.push(addr.trim().to_string());
} }
let config = Config::new( let config = match Config::new(
false, false,
token, token,
device_id, device_id,
@@ -154,7 +154,17 @@ fn new_sync(env: &mut JNIEnv, config: JObject) -> Result<VntUtilSync, Error> {
PunchModel::All, PunchModel::All,
port, port,
first_latency, first_latency,
); ) {
Ok(config) => config,
Err(e) => {
env.throw_new(
"java/lang/RuntimeException",
format!("vnt start error {}", e),
)
.expect("throw");
return Err(Error::JavaException);
}
};
match VntUtilSync::new(config) { match VntUtilSync::new(config) {
Ok(vnt_util) => Ok(vnt_util), Ok(vnt_util) => Ok(vnt_util),
Err(e) => { Err(e) => {
+1 -1
View File
@@ -1,6 +1,6 @@
[package] [package]
name = "vnt" name = "vnt"
version = "1.2.7" version = "1.2.8"
edition = "2021" edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+99 -186
View File
@@ -1,29 +1,28 @@
use std::collections::HashMap; use std::collections::HashMap;
use std::io::{Read, Write}; use std::io::{Read, Write};
use std::net::TcpStream;
use std::net::UdpSocket as StdUdpSocket; use std::net::UdpSocket as StdUdpSocket;
use std::net::{Ipv4Addr, Ipv6Addr, Shutdown, SocketAddr}; use std::net::{Ipv4Addr, Shutdown, SocketAddr};
use std::net::{SocketAddrV6, TcpStream};
use std::sync::Arc; use std::sync::Arc;
use std::time::{Duration, Instant}; use std::time::{Duration, Instant};
use std::{io, thread}; use std::{io, thread};
use crossbeam_utils::atomic::AtomicCell; use crossbeam_utils::atomic::AtomicCell;
use parking_lot::RwLock; use parking_lot::{Mutex, RwLock};
use tokio::net::UdpSocket; use tokio::net::UdpSocket;
use tokio::sync::watch::{channel, Receiver, Sender}; use tokio::sync::watch::{channel, Receiver, Sender};
use crate::channel::punch::NatType; use crate::channel::punch::NatType;
use crate::channel::{Route, RouteKey, Status, TCP_ID, UDP_ID, UDP_V6_ID}; use crate::channel::{Route, RouteKey, Status, TCP_ID, UDP_ID};
use crate::core::status::VntWorker; use crate::core::status::VntWorker;
use crate::handle::recv_handler::ChannelDataHandler; use crate::handle::recv_handler::ChannelDataHandler;
use crate::handle::CurrentDeviceInfo; use crate::handle::CurrentDeviceInfo;
pub struct ContextInner { pub struct ContextInner {
//udp用于打洞、服务端通信(可选) //udp用于打洞、服务端通信(可选)
pub(crate) main_channel: Arc<StdUdpSocket>, pub(crate) main_channel: StdUdpSocket,
pub(crate) main_channel_ipv6: Option<Arc<StdUdpSocket>>,
//在udp的基础上,可以选择使用tcp和服务端通信 //在udp的基础上,可以选择使用tcp和服务端通信
pub(crate) main_tcp_channel: Option<std::sync::mpsc::SyncSender<Vec<u8>>>, pub(crate) main_tcp_channel: Option<Mutex<TcpStream>>,
pub(crate) route_table: RwLock<HashMap<Ipv4Addr, Vec<(Route, AtomicCell<Instant>)>>>, pub(crate) route_table: RwLock<HashMap<Ipv4Addr, Vec<(Route, AtomicCell<Instant>)>>>,
pub(crate) status_receiver: Receiver<Status>, pub(crate) status_receiver: Receiver<Status>,
pub(crate) status_sender: Sender<Status>, pub(crate) status_sender: Sender<Status>,
@@ -40,9 +39,8 @@ pub struct Context {
impl Context { impl Context {
pub fn new( pub fn new(
main_channel: Arc<StdUdpSocket>, main_channel: StdUdpSocket,
main_channel_ipv6: Option<Arc<StdUdpSocket>>, main_tcp_channel: Option<TcpStream>,
main_tcp_channel: Option<std::sync::mpsc::SyncSender<Vec<u8>>>,
current_device: Arc<AtomicCell<CurrentDeviceInfo>>, current_device: Arc<AtomicCell<CurrentDeviceInfo>>,
_channel_num: usize, _channel_num: usize,
first_latency: bool, first_latency: bool,
@@ -50,9 +48,9 @@ impl Context {
//当前版本只支持一个通道 //当前版本只支持一个通道
let channel_num = 1; let channel_num = 1;
let (status_sender, status_receiver) = channel(Status::Cone); let (status_sender, status_receiver) = channel(Status::Cone);
let main_tcp_channel = main_tcp_channel.map(|e| Mutex::new(e));
let inner = Arc::new(ContextInner { let inner = Arc::new(ContextInner {
main_channel, main_channel,
main_channel_ipv6,
main_tcp_channel, main_tcp_channel,
route_table: RwLock::new(HashMap::with_capacity(16)), route_table: RwLock::new(HashMap::with_capacity(16)),
status_receiver, status_receiver,
@@ -75,26 +73,23 @@ impl Context {
} }
pub fn close(&self) -> io::Result<()> { pub fn close(&self) -> io::Result<()> {
let _ = self.inner.status_sender.send(Status::Close); let _ = self.inner.status_sender.send(Status::Close);
if let Ok(port) = self.main_local_ipv4_port() { if let Ok(port) = self.main_local_udp_port() {
let _ = StdUdpSocket::bind("127.0.0.1:0")?.send_to( let _ = StdUdpSocket::bind("127.0.0.1:0")?.send_to(
b"stop", b"stop",
SocketAddr::V4(std::net::SocketAddrV4::new(Ipv4Addr::LOCALHOST, port)), SocketAddr::V4(std::net::SocketAddrV4::new(Ipv4Addr::LOCALHOST, port)),
); );
} }
if let Ok(port) = self.main_local_ipv6_port() {
let _ = StdUdpSocket::bind("[::]:0")?.send_to(
b"stop",
SocketAddr::V6(std::net::SocketAddrV6::new(Ipv6Addr::LOCALHOST, port, 0, 0)),
);
}
if let Some(tcp) = &self.inner.main_tcp_channel { if let Some(tcp) = &self.inner.main_tcp_channel {
let _ = tcp.send(vec![]); tcp.lock().shutdown(Shutdown::Both)?;
} }
Ok(()) Ok(())
} }
pub fn is_main_tcp(&self) -> bool { pub fn is_main_tcp(&self) -> bool {
self.inner.main_tcp_channel.is_some() self.inner.main_tcp_channel.is_some()
} }
pub fn is_first_latency(&self) -> bool {
self.inner.first_latency
}
pub fn switch(&self, nat_type: NatType) { pub fn switch(&self, nat_type: NatType) {
match nat_type { match nat_type {
NatType::Symmetric => { NatType::Symmetric => {
@@ -111,41 +106,53 @@ impl Context {
pub fn switch_to_symmetric(&self) { pub fn switch_to_symmetric(&self) {
let _ = self.inner.status_sender.send(Status::Symmetric); let _ = self.inner.status_sender.send(Status::Symmetric);
} }
pub fn main_local_ipv4_port(&self) -> io::Result<u16> { pub fn main_local_udp_port(&self) -> io::Result<u16> {
self.inner.main_channel.local_addr().map(|k| k.port()) self.inner.main_channel.local_addr().map(|k| k.port())
} }
pub fn main_local_ipv6_port(&self) -> io::Result<u16> {
if let Some(ipv6) = &self.inner.main_channel_ipv6 {
ipv6.local_addr().map(|k| k.port())
} else {
Err(io::Error::new(io::ErrorKind::Other, "not ipv6"))
}
}
fn insert_udp(&self, id: usize, udp: Arc<UdpSocket>) { fn insert_udp(&self, id: usize, udp: Arc<UdpSocket>) {
self.inner.udp_map.write().insert(id, udp); self.inner.udp_map.write().insert(id, udp);
} }
fn remove_udp(&self, id: usize) { fn remove_udp(&self, id: usize) {
self.inner.udp_map.write().remove(&id); self.inner.udp_map.write().remove(&id);
} }
pub fn send_main_udp(&self, buf: &[u8], addr: SocketAddr) -> io::Result<usize> { #[inline]
if addr.is_ipv6() { pub fn send_main_udp(&self, buf: &[u8], mut addr: SocketAddr) -> io::Result<usize> {
if let Some(udp_ipv6) = &self.inner.main_channel_ipv6 { if let SocketAddr::V4(ipv4) = addr {
udp_ipv6.send_to(buf, addr) addr = SocketAddr::V6(SocketAddrV6::new(
} else { ipv4.ip().to_ipv6_mapped(),
Err(io::Error::new(io::ErrorKind::Other, "not ipv6")) ipv4.port(),
0,
0,
));
} }
} else {
self.inner.main_channel.send_to(buf, addr) self.inner.main_channel.send_to(buf, addr)
} }
#[inline]
pub fn send_main_tcp(&self, buf: &[u8]) -> io::Result<usize> {
if let Some(sender) = &self.inner.main_tcp_channel {
let mut stream = sender.lock();
let mut head = [0; 4];
let len = buf.len();
head[2] = (len >> 8) as u8;
head[3] = (len & 0xFF) as u8;
stream.write_all(&head)?;
stream.write_all(buf)?;
Ok(len)
} else {
return Err(io::Error::new(io::ErrorKind::NotFound, "tcp not found"));
}
} }
pub fn send_main(&self, buf: &[u8], addr: SocketAddr) -> io::Result<usize> { pub fn send_main(&self, buf: &[u8], addr: SocketAddr) -> io::Result<usize> {
if let Some(sender) = &self.inner.main_tcp_channel { if let Some(sender) = &self.inner.main_tcp_channel {
if sender.try_send(buf.to_vec()).is_ok() { let mut stream = sender.lock();
Ok(buf.len()) let mut head = [0; 4];
} else { let len = buf.len();
Err(io::Error::new(io::ErrorKind::Other, "send_main err")) head[2] = (len >> 8) as u8;
} head[3] = (len & 0xFF) as u8;
stream.write_all(&head)?;
stream.write_all(buf)?;
Ok(len)
} else { } else {
self.send_main_udp(buf, addr) self.send_main_udp(buf, addr)
} }
@@ -197,25 +204,8 @@ impl Context {
pub async fn send_by_key(&self, buf: &[u8], route_key: &RouteKey) -> io::Result<usize> { pub async fn send_by_key(&self, buf: &[u8], route_key: &RouteKey) -> io::Result<usize> {
match route_key.index { match route_key.index {
TCP_ID => { TCP_ID => self.send_main_tcp(buf),
if let Some(sender) = &self.inner.main_tcp_channel { UDP_ID => self.send_main_udp(buf, route_key.addr),
if sender.send(buf.to_vec()).is_ok() {
Ok(buf.len())
} else {
Err(io::Error::new(io::ErrorKind::Other, "send_by_key err"))
}
} else {
Err(io::Error::new(io::ErrorKind::Other, "send_by_key err"))
}
}
UDP_ID => self.inner.main_channel.send_to(buf, route_key.addr),
UDP_V6_ID => {
if let Some(udp_ipv6) = &self.inner.main_channel_ipv6 {
udp_ipv6.send_to(buf, route_key.addr)
} else {
Err(io::Error::new(io::ErrorKind::Other, "not ipv6 udp"))
}
}
_ => { _ => {
if let Some(udp) = self.get_udp_by_route(route_key) { if let Some(udp) = self.get_udp_by_route(route_key) {
return udp.send_to(buf, route_key.addr).await; return udp.send_to(buf, route_key.addr).await;
@@ -226,25 +216,8 @@ impl Context {
} }
pub fn try_send_by_key(&self, buf: &[u8], route_key: &RouteKey) -> io::Result<usize> { pub fn try_send_by_key(&self, buf: &[u8], route_key: &RouteKey) -> io::Result<usize> {
match route_key.index { match route_key.index {
TCP_ID => { TCP_ID => self.send_main_tcp(buf),
if let Some(sender) = &self.inner.main_tcp_channel { UDP_ID => self.send_main_udp(buf, route_key.addr),
if sender.try_send(buf.to_vec()).is_ok() {
Ok(buf.len())
} else {
Err(io::Error::new(io::ErrorKind::Other, "send_by_key err"))
}
} else {
Err(io::Error::new(io::ErrorKind::Other, "send_by_key err"))
}
}
UDP_ID => self.inner.main_channel.send_to(buf, route_key.addr),
UDP_V6_ID => {
if let Some(udp_ipv6) = &self.inner.main_channel_ipv6 {
udp_ipv6.send_to(buf, route_key.addr)
} else {
Err(io::Error::new(io::ErrorKind::Other, "not ipv6 udp"))
}
}
_ => { _ => {
if let Some(udp) = self.get_udp_by_route(route_key) { if let Some(udp) = self.get_udp_by_route(route_key) {
return udp.try_send_to(buf, route_key.addr); return udp.try_send_to(buf, route_key.addr);
@@ -271,8 +244,8 @@ impl Context {
.or_insert_with(|| Vec::with_capacity(4)); .or_insert_with(|| Vec::with_capacity(4));
let mut exist = false; let mut exist = false;
for (x, time) in list.iter_mut() { for (x, time) in list.iter_mut() {
if x.metric < route.metric { if x.metric < route.metric && !self.inner.first_latency {
//不能比当前的路径更长 //非优先延迟的情况下 不能比当前的路径更长
return; return;
} }
if x.route_key() == key { if x.route_key() == key {
@@ -289,12 +262,16 @@ impl Context {
if exist { if exist {
list.sort_by_key(|(k, _)| k.rt); list.sort_by_key(|(k, _)| k.rt);
} else { } else {
if route.metric == 1 && !self.inner.first_latency { let max_len = if self.inner.first_latency {
self.inner.channel_num + 1
} else {
if route.metric == 1 {
//非优先延迟的情况下 添加了直连的则排除非直连的 //非优先延迟的情况下 添加了直连的则排除非直连的
list.retain(|(k, _)| k.metric == 1); list.retain(|(k, _)| k.metric == 1);
} }
self.inner.channel_num
};
list.sort_by_key(|(k, _)| k.rt); list.sort_by_key(|(k, _)| k.rt);
let max_len = self.inner.channel_num;
if list.len() > max_len { if list.len() > max_len {
list.truncate(max_len); list.truncate(max_len);
} }
@@ -428,14 +405,17 @@ fn buf_channel_group(size: usize) -> (BufSenderGroup, BufReceiverGroup) {
impl Channel { impl Channel {
fn tcp_handle( fn tcp_handle(
tcp_r: &mut TcpStream, tcp_r: &mut TcpStream,
context: Context, context: &Context,
handler: ChannelDataHandler, handler: &ChannelDataHandler,
head_reserve: usize, head_reserve: usize,
) -> io::Result<()> { ) -> io::Result<()> {
let mut head = [0; 4]; let mut head = [0; 4];
let addr = tcp_r.peer_addr()?; let addr = tcp_r.peer_addr()?;
let key = RouteKey::new(TCP_ID, addr); let key = RouteKey::new(TCP_ID, addr);
loop { loop {
if context.is_close() {
return Ok(());
}
let mut buf = [0; 4096]; let mut buf = [0; 4096];
tcp_r.read_exact(&mut head)?; tcp_r.read_exact(&mut head)?;
let len = (((head[2] as u16) << 8) | head[3] as u16) as usize; let len = (((head[2] as u16) << 8) | head[3] as u16) as usize;
@@ -446,97 +426,57 @@ impl Channel {
)); ));
} }
tcp_r.read_exact(&mut buf[head_reserve..head_reserve + len])?; tcp_r.read_exact(&mut buf[head_reserve..head_reserve + len])?;
handler.handle(&mut buf, head_reserve, head_reserve + len, key, &context); handler.handle(&mut buf, head_reserve, head_reserve + len, key, context);
} }
} }
fn start_tcp( fn start_tcp(
worker: VntWorker,
mut tcp_stream: TcpStream, mut tcp_stream: TcpStream,
receiver: std::sync::mpsc::Receiver<Vec<u8>>,
context: Context, context: Context,
handler: ChannelDataHandler, handler: ChannelDataHandler,
head_reserve: usize, head_reserve: usize,
) { ) {
let current_device = context.inner.current_device.clone(); let current_device = context.inner.current_device.clone();
{ loop {
let mut tcp_r = tcp_stream.try_clone().unwrap(); if let Err(e) = tcp_stream.set_nodelay(true) {
let context = context.clone(); log::info!("set_nodelay:{:?}", e);
let handler = handler.clone(); }
thread::Builder::new() if let Err(e) = tcp_stream.set_write_timeout(Some(Duration::from_secs(3))) {
.name("tcp_reader".into()) log::info!("set_write_timeout:{:?}", e);
.spawn(move || { }
if let Err(e) = Self::tcp_handle(&mut tcp_r, context, handler, head_reserve) { if let Err(e) = tcp_stream.set_read_timeout(Some(Duration::from_secs(10))) {
log::info!("set_read_timeout:{:?}", e);
}
if let Err(e) = Self::tcp_handle(&mut tcp_stream, &context, &handler, head_reserve) {
log::info!("tcp链接断开:{:?}", e); log::info!("tcp链接断开:{:?}", e);
} }
if let Err(e) = tcp_r.shutdown(Shutdown::Both) {
log::info!("tcp链接关闭异常:{:?}", e);
}
})
.unwrap();
}
let mut head = [0; 4];
loop {
let data = match receiver.recv() {
Ok(data) => data,
Err(_) => {
break;
}
};
let len = data.len();
if len == 0 {
break;
}
head[2] = (len >> 8) as u8;
head[3] = (len & 0xFF) as u8;
let mut err = false;
if let Err(e) = tcp_stream.write_all(&head) {
err = true;
log::info!("发送失败,需要重连:{:?}", e);
} else if let Err(e) = tcp_stream.write_all(&data) {
err = true;
log::info!("发送失败,需要重连:{:?}", e);
}
if err {
if let Err(e) = tcp_stream.shutdown(Shutdown::Both) { if let Err(e) = tcp_stream.shutdown(Shutdown::Both) {
log::info!("tcp链接关闭异常:{:?}", e); log::info!("tcp链接关闭异常:{:?}", e);
} }
match TcpStream::connect(current_device.load().connect_server) { loop {
if context.is_close() {
return;
}
let device_info = current_device.load();
match TcpStream::connect(device_info.connect_server) {
Ok(tcp) => { Ok(tcp) => {
tcp.set_read_timeout(Some(Duration::from_secs(10))).unwrap(); tcp_stream = tcp.try_clone().unwrap();
tcp_stream = tcp; let mut guard = context.inner.main_tcp_channel.as_ref().unwrap().lock();
let mut tcp_r = tcp_stream.try_clone().unwrap(); *guard = tcp;
let context = context.clone(); break;
let handler = handler.clone();
thread::Builder::new()
.name("tcp_reader".into())
.spawn(move || {
if let Err(e) =
Self::tcp_handle(&mut tcp_r, context, handler, head_reserve)
{
log::info!("重连后 tcp链接断开:{:?}", e);
}
if let Err(e) = tcp_r.shutdown(Shutdown::Both) {
log::info!("重连后 tcp链接关闭异常:{:?}", e);
}
})
.unwrap();
} }
Err(e) => { Err(e) => {
log::info!("重连失败:{:?}", e); log::info!("重连失败,{},{:?}", device_info.connect_server, e);
thread::sleep(Duration::from_secs(3));
} }
} }
} }
} }
if let Err(e) = tcp_stream.shutdown(Shutdown::Both) {
log::info!("tcp链接关闭异常:{:?}", e);
}
worker.stop_all();
} }
pub async fn start( pub async fn start(
self, self,
mut worker: VntWorker, mut worker: VntWorker,
tcp: Option<(TcpStream, std::sync::mpsc::Receiver<Vec<u8>>)>, tcp: Option<TcpStream>,
head_reserve: usize, //头部预留字节 head_reserve: usize, //头部预留字节
symmetric_channel_num: usize, //对称网络,则再加一组监听,提升打洞成功率 symmetric_channel_num: usize, //对称网络,则再加一组监听,提升打洞成功率
relay: bool, relay: bool,
@@ -544,7 +484,7 @@ impl Channel {
) { ) {
let handler = self.handler.clone(); let handler = self.handler.clone();
let context = self.context; let context = self.context;
let main_channel = context.inner.main_channel.clone(); let main_channel = context.inner.main_channel.try_clone().unwrap();
let buf_sender = if parallel > 1 { let buf_sender = if parallel > 1 {
let (buf_sender, buf_receiver) = buf_channel_group(parallel); let (buf_sender, buf_receiver) = buf_channel_group(parallel);
let mut num = 0; let mut num = 0;
@@ -566,54 +506,26 @@ impl Channel {
} else { } else {
None None
}; };
if let Some((tcp_stream, receiver)) = tcp { if let Some(tcp_stream) = tcp {
let context = context.clone(); let context = context.clone();
let handler = handler.clone(); let handler = handler.clone();
let main_channel_tcp = worker.worker("main_channel_tcp"); let main_channel_tcp = worker.worker("main_channel_tcp");
thread::Builder::new() thread::Builder::new()
.name("main_channel_tcp".into()) .name("channel_tcp".into())
.spawn(move || { .spawn(move || {
Self::start_tcp( Self::start_tcp(tcp_stream, context, handler, head_reserve);
main_channel_tcp, drop(main_channel_tcp)
tcp_stream,
receiver,
context,
handler,
head_reserve,
)
})
.unwrap();
}
if let Some(main_channel_ipv6) = &context.inner.main_channel_ipv6 {
let worker = worker.worker("main_channel_ipv6");
let context = context.clone();
let main_channel_ipv6 = main_channel_ipv6.clone();
let handler = handler.clone();
let buf_sender = buf_sender.clone();
thread::Builder::new()
.name("ipv6-recv".into())
.spawn(move || {
log::info!("启动udp v6");
Self::main_start_(
worker,
context,
UDP_V6_ID,
main_channel_ipv6,
handler,
buf_sender,
head_reserve,
)
}) })
.unwrap(); .unwrap();
} }
{ {
let worker = worker.worker("main_channel_1"); let worker = worker.worker("main_channel_udp");
let context = context.clone(); let context = context.clone();
let main_channel = main_channel.clone(); let main_channel = main_channel.try_clone().unwrap();
let handler = handler.clone(); let handler = handler.clone();
let buf_sender = buf_sender.clone(); let buf_sender = buf_sender.clone();
thread::Builder::new() thread::Builder::new()
.name("ipv4-recv".into()) .name("channel_udp".into())
.spawn(move || { .spawn(move || {
log::info!("启动udp v4"); log::info!("启动udp v4");
Self::main_start_( Self::main_start_(
@@ -634,6 +546,7 @@ impl Channel {
} }
let mut cur_status = Status::Cone; let mut cur_status = Status::Cone;
let mut status_receiver = context.inner.status_receiver.clone(); let mut status_receiver = context.inner.status_receiver.clone();
let channel_num = context.inner.channel_num;
loop { loop {
tokio::select! { tokio::select! {
_=worker.stop_wait()=>{ _=worker.stop_wait()=>{
@@ -652,7 +565,7 @@ impl Channel {
continue; continue;
} }
cur_status = Status::Symmetric; cur_status = Status::Symmetric;
for _ in 0..symmetric_channel_num { for _ in 0..symmetric_channel_num - channel_num {
match UdpSocket::bind("0.0.0.0:0").await { match UdpSocket::bind("0.0.0.0:0").await {
Ok(udp) => { Ok(udp) => {
let udp = Arc::new(udp); let udp = Arc::new(udp);
@@ -683,7 +596,7 @@ impl Channel {
worker: VntWorker, worker: VntWorker,
context: Context, context: Context,
id: usize, id: usize,
udp: Arc<StdUdpSocket>, udp: StdUdpSocket,
handler: ChannelDataHandler, handler: ChannelDataHandler,
buf_sender: Option<BufSenderGroup>, buf_sender: Option<BufSenderGroup>,
head_reserve: usize, head_reserve: usize,
-1
View File
@@ -7,7 +7,6 @@ pub mod sender;
const TCP_ID: usize = 0; const TCP_ID: usize = 0;
const UDP_ID: usize = 1; const UDP_ID: usize = 1;
const UDP_V6_ID: usize = 2;
#[derive(Copy, Clone, Eq, PartialEq)] #[derive(Copy, Clone, Eq, PartialEq)]
pub enum Status { pub enum Status {
+23 -1
View File
@@ -52,7 +52,13 @@ impl NatInfo {
ipv6_addr: SocketAddrV6, ipv6_addr: SocketAddrV6,
mut nat_type: NatType, mut nat_type: NatType,
) -> Self { ) -> Self {
public_ips.retain(|ip| !ip.is_loopback() && !ip.is_private() && !ip.is_unspecified()); public_ips.retain(|ip| {
!ip.is_multicast()
&& !ip.is_broadcast()
&& !ip.is_unspecified()
&& !ip.is_loopback()
&& !ip.is_private()
});
if public_ips.len() > 1 { if public_ips.len() > 1 {
nat_type = NatType::Symmetric; nat_type = NatType::Symmetric;
} }
@@ -65,6 +71,20 @@ impl NatInfo {
nat_type, nat_type,
} }
} }
pub fn update_addr(&mut self, ip: Ipv4Addr, port: u16) {
if !ip.is_multicast()
&& !ip.is_broadcast()
&& !ip.is_unspecified()
&& !ip.is_loopback()
&& !ip.is_private()
&& port != 0
{
self.public_port = port;
if !self.public_ips.contains(&ip) {
self.public_ips.push(ip);
}
}
}
} }
#[derive(Clone)] #[derive(Clone)]
@@ -165,6 +185,7 @@ impl Punch {
self.port_index.insert(id, index); self.port_index.insert(id, index);
} }
NatType::Cone => { NatType::Cone => {
if nat_info.public_port != 0 {
let is_cone = self.context.is_cone(); let is_cone = self.context.is_cone();
for ip in nat_info.public_ips { for ip in nat_info.public_ips {
let addr = SocketAddr::V4(SocketAddrV4::new(ip, nat_info.public_port)); let addr = SocketAddr::V4(SocketAddrV4::new(ip, nat_info.public_port));
@@ -177,6 +198,7 @@ impl Punch {
} }
} }
} }
}
Ok(()) Ok(())
} }
+23 -29
View File
@@ -57,7 +57,6 @@ pub struct Vnt {
pub struct VntUtil { pub struct VntUtil {
config: Config, config: Config,
main_channel: UdpSocket, main_channel: UdpSocket,
main_channel_ipv6: Option<UdpSocket>,
main_tcp_channel: Option<TcpStream>, main_tcp_channel: Option<TcpStream>,
response: Option<RegResponse>, response: Option<RegResponse>,
iface: Option<(DeviceWriter, DeviceReader)>, iface: Option<(DeviceWriter, DeviceReader)>,
@@ -67,24 +66,14 @@ pub struct VntUtil {
impl VntUtil { impl VntUtil {
pub fn new(config: Config) -> io::Result<VntUtil> { pub fn new(config: Config) -> io::Result<VntUtil> {
let address: SocketAddr = format!("[::]:{}", config.port).parse().unwrap();
//单个udp用同步的性能更好,但是代理和多端口监听用异步更方便,这里将两者结合起来 //单个udp用同步的性能更好,但是代理和多端口监听用异步更方便,这里将两者结合起来
let main_channel = UdpSocket::bind(format!("0.0.0.0:{}", config.port))?; let socket = socket2::Socket::new(socket2::Domain::IPV6, socket2::Type::DGRAM, None)?;
socket.set_only_v6(false)?;
socket.bind(&address.into())?;
let main_channel: UdpSocket = socket.into();
main_channel.set_write_timeout(Some(Duration::from_secs(5)))?; main_channel.set_write_timeout(Some(Duration::from_secs(5)))?;
main_channel.set_read_timeout(Some(Duration::from_secs(2)))?; main_channel.set_read_timeout(Some(Duration::from_secs(2)))?;
let main_channel_ipv6 = if config.punch_model != PunchModel::IPv4 {
match UdpSocket::bind(format!("[::]:{}", config.port)) {
Ok(main_channel_ipv6) => {
main_channel_ipv6.set_write_timeout(Some(Duration::from_secs(5)))?;
Some(main_channel_ipv6)
}
Err(e) => {
log::warn!("绑定ipv6地址失败:{}", e);
None
}
}
} else {
None
};
let server_cipher = if config.server_encrypt { let server_cipher = if config.server_encrypt {
let mut key = [0u8; 32]; let mut key = [0u8; 32];
rand::thread_rng().fill(&mut key); rand::thread_rng().fill(&mut key);
@@ -95,7 +84,6 @@ impl VntUtil {
Ok(VntUtil { Ok(VntUtil {
config, config,
main_channel, main_channel,
main_channel_ipv6,
main_tcp_channel: None, main_tcp_channel: None,
response: None, response: None,
iface: None, iface: None,
@@ -248,15 +236,13 @@ impl VntUtil {
let (cone_sender, cone_receiver) = channel(3); let (cone_sender, cone_receiver) = channel(3);
let (symmetric_sender, symmetric_receiver) = channel(2); let (symmetric_sender, symmetric_receiver) = channel(2);
let (tcp_sender, tcp) = if let Some(main_tcp_channel) = self.main_tcp_channel { let (tcp_sender, tcp_receiver) = if let Some(main_tcp_channel) = self.main_tcp_channel {
let (tcp_sender, tcp_receiver) = std::sync::mpsc::sync_channel::<Vec<u8>>(100); (Some(main_tcp_channel.try_clone()?), Some(main_tcp_channel))
(Some(tcp_sender), Some((main_tcp_channel, tcp_receiver)))
} else { } else {
(None, None) (None, None)
}; };
let context = Context::new( let context = Context::new(
Arc::new(self.main_channel), self.main_channel,
self.main_channel_ipv6.map(|v| Arc::new(v)),
tcp_sender, tcp_sender,
current_device.clone(), current_device.clone(),
1, 1,
@@ -282,11 +268,10 @@ impl VntUtil {
let connect_status = Arc::new(AtomicCell::new(ConnectStatus::Connected)); let connect_status = Arc::new(AtomicCell::new(ConnectStatus::Connected));
let public_ip = response.public_ip; let public_ip = response.public_ip;
let public_port = response.public_port; let public_port = response.public_port;
let local_port = context.main_local_ipv4_port().unwrap_or(0); let local_port = context.main_local_udp_port().unwrap_or(0);
let local_ipv4_addr = crate::nat::local_ipv4_addr(local_port); let local_ipv4_addr = crate::nat::local_ipv4_addr(local_port);
let ipv6_port = context.main_local_ipv6_port().unwrap_or(0); let ipv6_addr = crate::nat::local_ipv6_addr(local_port);
let ipv6_addr = crate::nat::local_ipv6_addr(ipv6_port);
// NAT检测 // NAT检测
let nat_test = NatTest::new( let nat_test = NatTest::new(
config.stun_server.clone(), config.stun_server.clone(),
@@ -397,7 +382,7 @@ impl VntUtil {
let relay = config.relay; let relay = config.relay;
tokio::spawn(async move { tokio::spawn(async move {
channel channel
.start(channel_worker, tcp, 14, 65, relay, config.parallel) .start(channel_worker, tcp_receiver, 14, 65, relay, config.parallel)
.await .await
}); });
} }
@@ -614,13 +599,22 @@ impl Config {
punch_model: PunchModel, punch_model: PunchModel,
port: u16, port: u16,
first_latency: bool, first_latency: bool,
) -> Self { ) -> Result<Self, Error> {
for x in stun_server.iter_mut() { for x in stun_server.iter_mut() {
if !x.contains(":") { if !x.contains(":") {
x.push_str(":3478"); x.push_str(":3478");
} }
} }
Self { if token.is_empty() || token.len() > 128 {
return Err(Error::Stop(String::from("token too long")));
}
if device_id.is_empty() || device_id.len() > 128 {
return Err(Error::Stop(String::from("device_id too long")));
}
if name.is_empty() || name.len() > 128 {
return Err(Error::Stop(String::from("name too long")));
}
Ok(Self {
tap, tap,
token, token,
device_id, device_id,
@@ -645,6 +639,6 @@ impl Config {
punch_model, punch_model,
port, port,
first_latency, first_latency,
} })
} }
} }
+13 -4
View File
@@ -1,4 +1,4 @@
use std::net::SocketAddr; use std::net::{SocketAddr, SocketAddrV6};
use crate::channel::channel::Context; use crate::channel::channel::Context;
use crate::channel::RouteKey; use crate::channel::RouteKey;
@@ -168,16 +168,25 @@ fn send_recv(
} }
Ok(len) Ok(len)
} else { } else {
let server_address = if let SocketAddr::V4(ipv4) = server_address {
SocketAddr::V6(SocketAddrV6::new(
ipv4.ip().to_ipv6_mapped(),
ipv4.port(),
0,
0,
))
} else {
server_address
};
if let Err(e) = main_channel.send_to(send_buf, server_address) { if let Err(e) = main_channel.send_to(send_buf, server_address) {
return Err(HandshakeEnum::Other(format!("send error:{}", e))); return Err(HandshakeEnum::Other(format!("send error:{}", e)));
} }
match main_channel.recv_from(recv_buf) { match main_channel.recv_from(recv_buf) {
Ok((len, addr)) => { Ok((len, addr)) => {
if server_address != addr { if server_address != addr {
Err(HandshakeEnum::Other(format!("invalid data,from {}", addr))) log::warn!("请求{:?}和响应{:?}地址不一致", server_address, addr);
} else {
Ok(len)
} }
Ok(len)
} }
Err(e) => Err(HandshakeEnum::Other(format!("receiver error:{}", e))), Err(e) => Err(HandshakeEnum::Other(format!("receiver error:{}", e))),
} }
+7 -6
View File
@@ -3,15 +3,15 @@ use std::net::{Ipv4Addr, ToSocketAddrs};
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
use crossbeam_utils::atomic::AtomicCell;
use parking_lot::Mutex;
use rand::prelude::SliceRandom;
use crate::channel::idle::Idle; use crate::channel::idle::Idle;
use crate::channel::sender::ChannelSender; use crate::channel::sender::ChannelSender;
use crate::channel::Route; use crate::channel::Route;
use crate::cipher::Cipher; use crate::cipher::Cipher;
use crate::core::status::VntWorker; use crate::core::status::VntWorker;
use crossbeam_utils::atomic::AtomicCell;
use parking_lot::Mutex;
use rand::prelude::SliceRandom;
use crate::handle::{CurrentDeviceInfo, PeerDeviceInfo}; use crate::handle::{CurrentDeviceInfo, PeerDeviceInfo};
use crate::protocol::body::ENCRYPTION_RESERVED; use crate::protocol::body::ENCRYPTION_RESERVED;
use crate::protocol::control_packet::PingPacket; use crate::protocol::control_packet::PingPacket;
@@ -64,6 +64,7 @@ pub fn start_heartbeat(
worker.stop_all(); worker.stop_all();
}); });
} }
pub fn start_heartbeat_main( pub fn start_heartbeat_main(
mut worker: VntWorker, mut worker: VntWorker,
sender: ChannelSender, sender: ChannelSender,
@@ -200,7 +201,7 @@ async fn start_heartbeat_(
let src = current_dev.virtual_ip(); let src = current_dev.virtual_ip();
if count < 7 || count % 7 == 0 { if count % 10 == 7 {
let mut route_list: Option<Vec<(Ipv4Addr, Vec<Route>)>> = None; let mut route_list: Option<Vec<(Ipv4Addr, Vec<Route>)>> = None;
let peer_list = { device_list.lock().1.clone() }; let peer_list = { device_list.lock().1.clone() };
for peer in peer_list { for peer in peer_list {
@@ -222,7 +223,7 @@ async fn start_heartbeat_(
{ {
log::warn!("virtual_ip:{},route:{:?},e:{:?}", peer.virtual_ip, route, e); log::warn!("virtual_ip:{},route:{:?},e:{:?}", peer.virtual_ip, route, e);
} }
if route.is_p2p() { if route.is_p2p() && !sender.is_first_latency() {
continue; continue;
} }
} else { } else {
+1 -2
View File
@@ -592,9 +592,8 @@ impl ChannelDataHandler {
.build() .build()
.unwrap() .unwrap()
.block_on(async move { .block_on(async move {
let local_port = context.main_local_ipv4_port().unwrap_or(0); let local_port = context.main_local_udp_port().unwrap_or(0);
let local_ipv4_addr = nat::local_ipv4_addr(local_port); let local_ipv4_addr = nat::local_ipv4_addr(local_port);
let local_port = context.main_local_ipv6_port().unwrap_or(0);
let ipv6_addr = nat::local_ipv6_addr(local_port); let ipv6_addr = nat::local_ipv6_addr(local_port);
let nat_info = nat_test let nat_info = nat_test
.re_test( .re_test(
+11 -2
View File
@@ -1,6 +1,6 @@
use crossbeam_utils::atomic::AtomicCell; use crossbeam_utils::atomic::AtomicCell;
use std::io::{Read, Write}; use std::io::{Read, Write};
use std::net::{Ipv4Addr, SocketAddr}; use std::net::{Ipv4Addr, SocketAddr, SocketAddrV6};
use std::time::{Duration, Instant}; use std::time::{Duration, Instant};
use crate::channel::sender::ChannelSender; use crate::channel::sender::ChannelSender;
@@ -82,13 +82,22 @@ pub fn registration(
} }
&mut recv_buf[4..len] &mut recv_buf[4..len]
} else { } else {
let server_address = match server_address {
SocketAddr::V4(ipv4) => SocketAddr::V6(SocketAddrV6::new(
ipv4.ip().to_ipv6_mapped(),
ipv4.port(),
0,
0,
)),
SocketAddr::V6(_) => server_address,
};
if let Err(e) = main_channel.send_to(buf, server_address) { if let Err(e) = main_channel.send_to(buf, server_address) {
return Err(ReqEnum::Other(format!("send error:{}", e))); return Err(ReqEnum::Other(format!("send error:{}", e)));
} }
match main_channel.recv_from(&mut recv_buf) { match main_channel.recv_from(&mut recv_buf) {
Ok((len, addr)) => { Ok((len, addr)) => {
if server_address != addr { if server_address != addr {
return Err(ReqEnum::Other(format!("invalid data,from {}", addr))); log::warn!("请求{:?}和响应{:?}地址不一致", server_address, addr);
} }
&mut recv_buf[..len] &mut recv_buf[..len]
} }
+1 -1
View File
@@ -1,5 +1,5 @@
use crate::error::Error; use crate::error::Error;
pub const VNT_VERSION: &'static str = "1.2.7"; pub const VNT_VERSION: &'static str = "1.2.8";
pub type Result<T> = std::result::Result<T, Error>; pub type Result<T> = std::result::Result<T, Error>;
pub mod channel; pub mod channel;
+1 -12
View File
@@ -111,19 +111,8 @@ impl NatTest {
self.info.lock().clone() self.info.lock().clone()
} }
pub fn update_addr(&self, ip: Ipv4Addr, port: u16) { pub fn update_addr(&self, ip: Ipv4Addr, port: u16) {
if !ip.is_multicast()
&& !ip.is_broadcast()
&& !ip.is_unspecified()
&& !ip.is_loopback()
&& !ip.is_private()
&& port != 0
{
let mut guard = self.info.lock(); let mut guard = self.info.lock();
guard.public_port = port; guard.update_addr(ip, port)
if !guard.public_ips.contains(&ip) {
guard.public_ips.push(ip);
}
}
} }
pub async fn re_test( pub async fn re_test(
&self, &self,