From 9155471c265fbf920df6c527a5282471ef3fbce0 Mon Sep 17 00:00:00 2001 From: lubeilin <1791778603@qq.com> Date: Fri, 19 Apr 2024 16:28:49 +0800 Subject: [PATCH] =?UTF-8?q?=E5=8E=BB=E9=99=A4=E5=A4=9A=E4=BD=99=E4=BB=A3?= =?UTF-8?q?=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- vnt/src/handle/interface/adapter.rs | 216 ------------------------- vnt/src/handle/interface/mod.rs | 242 ---------------------------- 2 files changed, 458 deletions(-) delete mode 100644 vnt/src/handle/interface/adapter.rs delete mode 100644 vnt/src/handle/interface/mod.rs diff --git a/vnt/src/handle/interface/adapter.rs b/vnt/src/handle/interface/adapter.rs deleted file mode 100644 index 1fee951..0000000 --- a/vnt/src/handle/interface/adapter.rs +++ /dev/null @@ -1,216 +0,0 @@ -use std::net::Ipv4Addr; -use std::{io, process, thread}; -use std::sync::Arc; -use std::sync::mpsc::{Receiver, SyncSender, TrySendError}; -use crossbeam_utils::atomic::AtomicCell; -use tun::Device; -use tun::device::IFace; -use crate::handle::callback::DeviceConfig; -use crate::protocol::NetPacket; -use crate::util::{BufBlock, BufPool, GroupSyncSender, StopManager}; - -pub struct TunAdapter { - #[cfg(any(target_os = "windows", target_os = "linux"))] is_tap: bool, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] device_name: Option, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] mtu: u32, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] route_record: Vec<(Ipv4Addr, Ipv4Addr)>, - device: Option>, - buf_pool: BufPool, - stop_manager: StopManager, - receiver_stage: Option>>, - sender_stage: Option>>, -} -impl TunAdapter { - pub fn new( - #[cfg(any(target_os = "windows", target_os = "linux"))] is_tap: bool, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] device_name: Option, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] mtu: u32, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] route_record: Vec<(Ipv4Addr, Ipv4Addr)>, - buf_pool: BufPool, - stop_manager: StopManager, - receiver: Receiver>, - sender: SyncSender>, - )->Self{ - Self{ - #[cfg(any(target_os = "windows", target_os = "linux"))] is_tap, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] device_name, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] mtu, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] route_record, - device: None, - buf_pool, - stop_manager, - receiver_stage: Some(receiver), - sender_stage: Some(sender), - } - } -} - -impl TunAdapter { - pub fn device(&mut self, #[cfg(target_os = "android")] device_fd: u32) -> io::Result<()> { - if self.device.is_some() { - return Ok(()); - } else { - let device = create_device(#[cfg(any(target_os = "windows", target_os = "linux"))] self.is_tap, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] self.device_name.clone(), - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] self.mtu, - #[cfg(target_os = "android")] device_fd, )?; - let device = Arc::new(device); - self.device.replace(device); - { - let device = device.clone(); - let buf_pool = self.buf_pool.clone(); - let stop_manager = self.stop_manager.clone(); - let sender = self.sender_stage.take().unwrap(); - thread::Builder::new().name("tun-read".into()).spawn(move || { - loop { - let mut buf_block = buf_pool.alloc(); - #[cfg(not(target_os = "macos"))] - let start = 12; - #[cfg(target_os = "macos")] - let start = 8; - match device.read(&mut buf_block.as_mut()[start..]) { - Ok(len) => { - buf_block.as_mut()[..12].fill(0); - buf_block.set_data_len(start + len); - if let Err(e) = sender.try_send(buf_block) { - match e { - TrySendError::Full(_) => { - log::warn!("发生丢包"); - } - TrySendError::Disconnected(_) => { - break; - } - } - } - } - Err(e) => { - log::warn!("{:?}",e); - break; - } - } - } - stop_manager.stop(); - }).unwrap(); - } - { - let device = device.clone(); - let stop_manager = self.stop_manager.clone(); - let receiver = self.receiver_stage.take().unwrap(); - - thread::Builder::new().name("tun-write".into()).spawn(move || { - while let Ok(data) = receiver.recv() { - if let Err(e) = device.write(data.as_data()) { - log::warn!("写入网卡失败:{}",e); - break; - } - } - stop_manager.stop(); - }).unwrap(); - } - } - } - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] - pub fn change_ip(&mut self, info: DeviceConfig) -> io::Result<()> { - let device = if let Some(device) = &self.device { - device - } else { - return Err(io::Error::new(io::ErrorKind::NotFound, "IFace")); - }; - device.set_ip(info.virtual_ip, info.virtual_netmask)?; - for (dest, mask) in self.route_record.drain(..) { - if let Err(e) = self.device.delete_route(dest, mask) { - log::warn!("删除路由失败 ={:?}", e); - } - } - if let Err(e) = device.add_route(info.virtual_network, info.virtual_netmask, 1) - { - log::warn!("添加默认路由失败 ={:?}", e); - } else { - self.route_record.push((info.virtual_network, info.virtual_netmask)); - } - if let Err(e) = device - .add_route(Ipv4Addr::BROADCAST, Ipv4Addr::BROADCAST, 1) - { - log::warn!("添加广播路由失败 ={:?}", e); - } else { - self.route_record.push((Ipv4Addr::BROADCAST, Ipv4Addr::BROADCAST)); - } - - if let Err(e) = device.add_route( - Ipv4Addr::from([224, 0, 0, 0]), - Ipv4Addr::from([240, 0, 0, 0]), - 1, - ) { - log::warn!("添加组播路由失败 ={:?}", e); - } else { - self.route_record.push(( - Ipv4Addr::from([224, 0, 0, 0]), - Ipv4Addr::from([240, 0, 0, 0]), - )); - } - - for (dest, mask) in info.external_route { - if let Err(e) = self.device.add_route(dest, mask, 1) { - log::warn!("添加路由失败 ={:?}", e); - } else { - self.route_record.push((dest, mask)); - } - } - Ok(()) - } -} - -#[cfg(any(target_os = "windows", target_os = "linux"))] -const DEFAULT_TUN_NAME: &str = "vnt-tun"; -#[cfg(any(target_os = "windows", target_os = "linux"))] -const DEFAULT_TAP_NAME: &str = "vnt-tap"; - -pub fn create_device(#[cfg(any(target_os = "windows", target_os = "linux"))] is_tap: bool, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] device_name: Option, - #[cfg(any(target_os = "windows", target_os = "linux", target_os = "macos"))] mtu: u32, - #[cfg(target_os = "android")] device_fd: u32, ) -> io::Result { - #[cfg(any(target_os = "windows", target_os = "linux"))] - let default_name: &str = if is_tap { - DEFAULT_TAP_NAME - } else { - DEFAULT_TUN_NAME - }; - #[cfg(target_os = "linux")] - let device = { - let device_name = device_name - .unwrap_or(default_name.to_string()); - if &device_name == default_name { - delete_device(default_name); - } - Device::new(Some(device_name), is_tap)? - }; - #[cfg(target_os = "macos")] - let device = Device::new(device_name)?; - #[cfg(target_os = "windows")] - let device = Device::new( - device_name - .unwrap_or(default_name.to_string()), - is_tap, - )?; - #[cfg(target_os = "android")] - let device = Device::new(device_fd as _)?; - #[cfg(not(target_os = "android"))] - device.set_mtu(mtu)?; - Ok(device) -} - -#[cfg(target_os = "linux")] -fn delete_device(name: &str) { - // 删除默认网卡,此操作有风险,后续可能去除 - use std::process::Command; - let cmd = format!("ip link delete {}", name); - let delete_tun = Command::new("sh") - .arg("-c") - .arg(&cmd) - .output() - .expect("sh exec error!"); - if !delete_tun.status.success() { - log::info!("{},{:?}",cmd, delete_tun); - } -} - diff --git a/vnt/src/handle/interface/mod.rs b/vnt/src/handle/interface/mod.rs deleted file mode 100644 index 5355ceb..0000000 --- a/vnt/src/handle/interface/mod.rs +++ /dev/null @@ -1,242 +0,0 @@ -use std::{io, thread}; -use std::net::Ipv4Addr; -use std::sync::Arc; -use std::sync::mpsc::Receiver; - -use crossbeam_utils::atomic::AtomicCell; -use parking_lot::Mutex; - -use packet::icmp::icmp::IcmpPacket; -use packet::icmp::Kind; -use packet::ip::ipv4; -use packet::ip::ipv4::packet::IpV4Packet; -use packet::ip::ipv4::protocol::Protocol; - -use crate::channel::context::Context; -use crate::cipher::Cipher; -use crate::external_route::ExternalRoute; -use crate::handle::{check_dest, CurrentDeviceInfo, PeerDeviceInfo}; -use crate::ip_proxy::{IpProxyMap, ProxyHandler}; -use crate::protocol; -use crate::protocol::{ip_turn_packet, MAX_TTL, NetPacket, Version}; -use crate::protocol::body::ENCRYPTION_RESERVED; -use crate::protocol::ip_turn_packet::BroadcastPacket; -use crate::util::{BufBlock, SingleU64Adder, StopManager}; -pub mod adapter; -pub fn start( - receivers: Vec>, - context: Context, - current_device: Arc>, - ip_route: ExternalRoute, - #[cfg(feature = "ip_proxy")] ip_proxy_map: Option, - client_cipher: Cipher, - server_cipher: Cipher, - device_list: Arc)>>, -) -> io::Result<()> { - for (index,receiver) in receivers.into_iter().enumerate() { - let context = context.clone(); - let current_device = current_device.clone(); - let ip_route = ip_route.clone(); - #[cfg(feature = "ip_proxy")] - let ip_proxy_map = ip_proxy_map.clone(); - let client_cipher = client_cipher.clone(); - let server_cipher = server_cipher.clone(); - let device_list = device_list.clone(); - thread::Builder::new() - .name(format!("IFace-{}", index)) - .spawn(move || { - while let Ok(mut data) = receiver.recv() { - let data_len = data.data_len(); - let buf = data.as_start_mut(); - if data_len==0{ - break; - } - match handle( - &context, - buf, - data_len, - current_device.load(), - &ip_route, - #[cfg(feature = "ip_proxy")] - &ip_proxy_map, - &client_cipher, - &server_cipher, - &device_list, - ) { - Ok(_) => {} - Err(e) => { - log::warn!("{:?}", e) - } - } - } - })?; - } - Ok(()) -} - - -/// 实现一个原地发送,必须保证是如下结构 -/// |12字节开头|ip报文|至少1024字节结尾| -/// -pub fn handle( - context: &Context, - buf: &mut [u8], - data_len: usize, //数据总长度=12+ip包长度 - current_device: CurrentDeviceInfo, - ip_route: &ExternalRoute, - #[cfg(feature = "ip_proxy")] proxy_map: &Option, - client_cipher: &Cipher, - server_cipher: &Cipher, - device_list: &Mutex<(u16, Vec)>, -) -> io::Result<()> { - let ipv4_packet = IpV4Packet::new(&buf[12..data_len])?; - let protocol = ipv4_packet.protocol(); - let src_ip = ipv4_packet.source_ip(); - let mut dest_ip = ipv4_packet.destination_ip(); - let mut net_packet = NetPacket::new0(data_len, buf)?; - net_packet.set_version(Version::V1); - net_packet.set_protocol(protocol::Protocol::IpTurn); - net_packet.set_transport_protocol(ip_turn_packet::Protocol::Ipv4.into()); - net_packet.first_set_ttl(6); - net_packet.set_source(src_ip); - net_packet.set_destination(dest_ip); - if dest_ip == current_device.virtual_gateway { - // 发到网关的加密方式不一样,要单独处理 - if protocol == Protocol::Icmp { - net_packet.set_gateway_flag(true); - server_cipher.encrypt_ipv4(&mut net_packet)?; - context.send_default(net_packet.buffer(), current_device.connect_server)?; - } - return Ok(()); - } - if dest_ip.is_multicast() { - //当作广播处理 - dest_ip = Ipv4Addr::BROADCAST; - net_packet.set_destination(Ipv4Addr::BROADCAST); - } - if dest_ip.is_broadcast() || current_device.broadcast_ip == dest_ip { - // 广播 发送到直连目标 - client_cipher.encrypt_ipv4(&mut net_packet)?; - broadcast( - server_cipher, - context, - &mut net_packet, - ¤t_device, - device_list, - )?; - return Ok(()); - } - if !check_dest( - dest_ip, - current_device.virtual_netmask, - current_device.virtual_network, - ) { - if let Some(r_dest_ip) = ip_route.route(&dest_ip) { - //路由的目标不能是自己 - if r_dest_ip == src_ip { - return Ok(()); - } - //需要修改目的地址 - dest_ip = r_dest_ip; - net_packet.set_destination(r_dest_ip); - } else { - return Ok(()); - } - } - #[cfg(feature = "ip_proxy")] - if let Some(proxy_map) = proxy_map { - let mut ipv4_packet = IpV4Packet::new(net_packet.payload_mut())?; - proxy_map.send_handle(&mut ipv4_packet)?; - } - client_cipher.encrypt_ipv4(&mut net_packet)?; - context.send_ipv4_by_id( - net_packet.buffer(), - &dest_ip, - current_device.connect_server, - current_device.status.online(), - ) -} - -fn broadcast( - server_cipher: &Cipher, - sender: &Context, - net_packet: &mut NetPacket<&mut [u8]>, - current_device: &CurrentDeviceInfo, - device_list: &Mutex<(u16, Vec)>, -) -> io::Result<()> { - let list: Vec = device_list - .lock() - .1 - .iter() - .filter(|info| info.status.is_online()) - .map(|info| info.virtual_ip) - .collect(); - const MAX_COUNT: usize = 8; - let mut p2p_ips = Vec::with_capacity(8); - let mut relay_ips = Vec::with_capacity(8); - let mut overflow = false; - for (index, peer_ip) in list.into_iter().enumerate() { - if index > MAX_COUNT { - overflow = true; - break; - } - if let Some(route) = sender.route_table.route_one_p2p(&peer_ip) { - if sender - .send_by_key(net_packet.buffer(), route.route_key()) - .is_ok() - { - p2p_ips.push(peer_ip); - continue; - } - } - relay_ips.push(peer_ip); - } - if !overflow && relay_ips.is_empty() { - //全部p2p,不需要服务器中转 - return Ok(()); - } - - if p2p_ips.is_empty() { - //都没有p2p则直接由服务器转发 - if current_device.status.online() { - sender.send_default(net_packet.buffer(), current_device.connect_server)?; - } - return Ok(()); - } - if !overflow && relay_ips.len() == 2 { - // 如果转发的ip数不多就直接发 - for peer_ip in relay_ips { - //非直连的广播要改变目的地址,不然服务端收到了会再次广播 - net_packet.set_destination(peer_ip); - sender.send_ipv4_by_id( - net_packet.buffer(), - &peer_ip, - current_device.connect_server, - current_device.status.online(), - )?; - } - return Ok(()); - } - if current_device.status.offline() { - //离线的不再转发 - return Ok(()); - } - let buf = vec![0u8; 12 + 1 + p2p_ips.len() * 4 + net_packet.data_len() + ENCRYPTION_RESERVED]; - //剩余的发送到服务端,需要告知哪些已发送过 - let mut server_packet = NetPacket::new_encrypt(buf)?; - server_packet.set_version(Version::V1); - server_packet.set_gateway_flag(true); - server_packet.first_set_ttl(MAX_TTL); - server_packet.set_source(net_packet.source()); - //使用对应的目的地址 - server_packet.set_destination(net_packet.destination()); - server_packet.set_protocol(protocol::Protocol::IpTurn); - server_packet.set_transport_protocol(ip_turn_packet::Protocol::Ipv4Broadcast.into()); - - let mut broadcast = BroadcastPacket::unchecked(server_packet.payload_mut()); - broadcast.set_address(&p2p_ips)?; - broadcast.set_data(net_packet.buffer())?; - server_cipher.encrypt_ipv4(&mut server_packet)?; - sender.send_default(server_packet.buffer(), current_device.connect_server) -} -