2025-05-12 10:37:16 +08:00

176 lines
4.8 KiB
Rust
Executable File

use sdlan_sn_rs::{
config::{AF_INET, AF_INET6},
utils::{Result, SDLanError},
};
use std::net::{IpAddr, Ipv4Addr, Ipv6Addr, SocketAddr};
use tokio::net::ToSocketAddrs;
use tracing::{debug, error};
use sdlan_sn_rs::peer::SdlanSock;
use tokio::net::UdpSocket;
use crate::network::Node;
#[allow(unused)]
pub struct SocketV6 {
ipv6: Option<Ipv4Addr>,
port: u16,
has_v6: bool,
}
pub struct Socket {
udp: UdpSocket,
}
impl Socket {
pub async fn send_to<A: ToSocketAddrs>(&self, buf: &[u8], target: A) -> Result<usize> {
let m = self.udp.send_to(buf, target).await?;
Ok(m)
}
pub fn get_local_port(&self) -> u16 {
match self.udp.local_addr() {
Ok(addr) => addr.port(),
Err(_e) => 0,
}
}
pub async fn recv_from(&self, buf: &mut [u8]) -> Result<(usize, SocketAddr)> {
let m = self.udp.recv_from(buf).await?;
Ok(m)
}
pub fn ttl(&self) -> Result<u32> {
if let Ok(v) = self.udp.ttl() {
Ok(v)
} else {
Err(SDLanError::NormalError("no ttl found"))
}
}
pub fn set_ttl(&self, ttl: u32) -> Result<()> {
if let Ok(_) = self.udp.set_ttl(ttl) {
Ok(())
} else {
Err(SDLanError::NormalError("failed to set ttl"))
}
}
pub async fn build_v6(v6: Ipv6Addr, port: u16) -> Result<Self> {
let udp = UdpSocket::bind(format!("[{}]:{}", v6, port)).await?;
Ok(Self { udp })
}
pub async fn build(port: u16, bind_any: bool, join_multicast: bool, tos: u32) -> Result<Self> {
let addr = match bind_any {
true => "0.0.0.0",
false => "127.0.0.1",
};
let addr = format!("{}:{}", addr, port);
let udp = UdpSocket::bind(&addr).await?;
if join_multicast {
if let Err(e) =
udp.join_multicast_v4(Ipv4Addr::new(224, 0, 0, 69), Ipv4Addr::new(0, 0, 0, 0))
{
error!("failed to join multicast: {}", e.to_string());
} else {
debug!("{} joined multicast ok", addr);
}
}
if tos != 0 {
if let Err(e) = udp.set_tos(tos) {
error!("failed to set tos: {}", e.to_string());
}
}
Ok(Self { udp })
}
}
/*
pub async fn send_to_sock_v4_and_v6(
// sk: &Socket,
eee: &Node,
content: &[u8],
sock: &SdlanSock,
v6: &Option<V6Info>,
) -> Result<()> {
let _ = send_to_sock(&eee, content, sock).await;
if let Some(v6) = v6 {
// let sk6 = eee.udp_sock_v6.read().unwrap().clone();
let sock = SdlanSock {
family: AF_INET6,
port: v6.port,
v4: [0; 4],
v6: v6.v6,
};
let _ = send_to_sock(eee, content, &sock).await;
}
Ok(())
}
*/
#[allow(unused)]
pub fn get_socketaddr_from_sock(s: &SdlanSock) -> SocketAddr {
let addr = SocketAddr::new(IpAddr::V4(Ipv4Addr::from(s.v4)), s.port);
addr
}
pub async fn send_to_sock(
// sk: &Socket,
eee: &Node,
content: &[u8],
sock: &SdlanSock,
// v6: &Option<V6Info>,
) -> Result<()> {
match sock.family {
AF_INET => {
// sockv4
let addr = SocketAddr::new(IpAddr::V4(Ipv4Addr::from(sock.v4)), sock.port);
// println!("udp sock v4 send to {}", addr);
eee.udp_sock_v4.send_to(content, addr).await?;
return Ok(());
}
AF_INET6 => {
// sock v6
let sk = eee.udp_sock_v6.read().unwrap().clone();
match sk.as_ref() {
None => {
error!("ipv6 not opened, not responding");
return Ok(());
}
Some(sk) => {
let addr = SocketAddr::new(IpAddr::V6(Ipv6Addr::from(sock.v6)), sock.port);
debug!("send with ipv6");
sk.send_to(content, addr).await?;
return Ok(());
}
}
}
other => {
error!("unknown family {}, aborting", other);
return Err(SDLanError::NormalError("unknown family"));
}
}
}
/*
pub async fn send_to_sock(sk: &Socket, content: &[u8], sock: &SdlanSock) -> Result<usize> {
match sock.family {
AF_INET => {
let addr = SocketAddr::new(IpAddr::V4(Ipv4Addr::from(sock.v4)), sock.port);
let n = sk.send_to(content, addr).await?;
return Ok(n);
}
AF_INET6 => {
let addr = SocketAddr::new(IpAddr::V6(Ipv6Addr::from(sock.v6)), sock.port);
let n = sk.send_to(content, addr).await?;
return Ok(n);
}
other => {
error!("AF family {} not implemented", other);
return Ok(0);
}
}
}
*/