ipv6 p2p is ok

This commit is contained in:
asxalex 2024-11-28 16:09:49 +08:00
parent c098a3c421
commit 240a3d263e
6 changed files with 115 additions and 45 deletions

View File

@ -14,6 +14,9 @@ pb:
cargo run --bin build_pb
mv src/pb/_.rs src/pb/message.rs
libtun-so-clang:
cd src/network && clang -fPIC -shared -o libtuntap.so tuntap.c && cd -
libtun-so:
cd src/network && gcc -fPIC -shared -o libtuntap.so tuntap.c && cd -

View File

@ -1,6 +1,6 @@
use sdlan_sn_rs::utils::Mac;
pub const REGISTER_INTERVAL: u8 = 20;
pub const REGISTER_INTERVAL: u8 = 3;
pub const REGISTER_SUPER_INTERVAL: u16 = 20;
pub const MULITCAST_V4: [u8; 4] = [224, 0, 0, 69];

View File

@ -12,7 +12,7 @@ use crate::pb::{
encode_to_tcp_message, encode_to_udp_message, SdlDevAddr, SdlRegisterSuper,
SdlRegisterSuperAck, SdlRegisterSuperNak, SdlSendRegisterEvent, SdlStunRequest, Sdlv6Info,
};
use crate::tcp::{init_tcp_conn, EventType, NakMsgCode, PacketType, SdlanTcp};
use crate::tcp::{init_tcp_conn, EventType, NakMsgCode, NatType, PacketType, SdlanTcp};
use crate::utils::{send_to_sock, CommandLine};
use crate::ConnectionState;
use sdlan_sn_rs::config::AF_INET;
@ -212,11 +212,18 @@ async fn handle_tcp_event(edge: &'static Node, eventtype: EventType, eventprotob
Err(_e) => NULL_MAC,
};
let remote_nat_byte = reg.nat_type as u8;
let remote_nat = match remote_nat_byte.try_into() {
Ok(t) => t,
Err(_) => NatType::NoNat,
};
check_peer_registration_needed(
edge,
true,
false,
dst_mac,
// &v6_sock,
remote_nat,
&v6_sock,
&SdlanSock {
family: AF_INET,
@ -493,29 +500,28 @@ pub async fn loop_socket_v4(
is_multicast_sock: bool,
) {
debug!("loop sock v4");
let cancel_clone = cancel.clone();
tokio::spawn(async move {
loop {
tokio::select! {
_ = cancel_clone.cancelled() => {
break;
}
_ = tokio::time::sleep(Duration::from_secs(10)) => {
if !is_multicast_sock {
send_stun_request(eee).await;
}
}
}
}
});
loop {
tokio::select! {
_ = cancel.cancelled() => {
break;
}
_ = read_and_parse_packet(eee, socket, Some(Duration::from_secs(10)), is_multicast_sock) => { }
_ = tokio::time::sleep(Duration::from_secs(10)) => {
if !is_multicast_sock {
send_stun_request(eee).await;
}
/*
let req = SdlStunRequest {
cookie: 0,
client_id: eee.config.node_uuid.clone(),
network_id: eee.network_id.load(Ordering::Relaxed),
ip: eee.device_config.get_ip(),
nat_type: 0,
};
let msg = encode_to_udp_message(Some(req), PacketType::StunRequest as u8).unwrap();
if let Err(e) = send_to_sock(eee, &msg, &eee.config.super_nodes[eee.config.super_node_index.load(Ordering::Relaxed) as usize]).await {
error!("failed to send to sock: {:?}", e);
}*/
}
}
}
debug!("loop_socket_v4 exited");
@ -633,6 +639,7 @@ async fn find_peer_destination(eee: &'static Node, dst_mac: Mac) -> (SdlanSock,
let now = get_current_timestamp();
if now - dst.last_p2p.load(Ordering::Relaxed) >= ((dst.timeout / 2) as u64) {
// too much time elapsed since we saw the peer, need to register again
error!("last p2p is too old, deleting from known_peers");
eee.known_peers.delete_peer_with_mac(&dst_mac);
result = eee.config.super_nodes
[eee.config.super_node_index.load(Ordering::Relaxed) as usize]

View File

@ -10,10 +10,7 @@ use tokio::{net::UdpSocket, sync::mpsc::Receiver};
use tokio_util::sync::CancellationToken;
use tracing::error;
use crate::{
network::{loop_socket_v4, loop_socket_v6},
utils::Socket,
};
use crate::{network::loop_socket_v6, utils::Socket};
use super::Node;
@ -21,11 +18,16 @@ pub async fn run_ipv6(edge: &'static Node, mut v6_may_change: Receiver<bool>) {
v6_may_change.recv().await;
loop {
tokio::time::sleep(Duration::from_secs(1)).await;
let ipv6 = get_current_ipv6();
let mut ipv6 = get_current_ipv6();
if ipv6.is_none() {
v6_may_change.recv().await;
continue;
tokio::time::sleep(Duration::from_secs(5)).await;
ipv6 = get_current_ipv6();
if ipv6.is_none() {
v6_may_change.recv().await;
continue;
}
}
// ipv6 is not none
let ipv6 = ipv6.unwrap();
/*

View File

@ -513,8 +513,8 @@ impl PeerMap {
None
}
pub fn delete_peer_with_mac(&self, mac: &Mac) {
self.peers.remove(mac);
pub fn delete_peer_with_mac(&self, mac: &Mac) -> Option<(Mac, Arc<EdgePeer>)> {
self.peers.remove(mac)
}
pub fn insert_peer(&self, mac: Mac, p: Arc<EdgePeer>) {
@ -552,7 +552,7 @@ impl NodeStats {
use sdlan_sn_rs::peer::SdlanSock;
use crate::config::{self, MULTICAST_PORT, REGISTER_INTERVAL};
use crate::config::{self, MULTICAST_PORT, REGISTER_INTERVAL, REGISTER_SUPER_INTERVAL};
pub struct NodeConfig {
// node name
pub name: String,
@ -641,7 +641,7 @@ impl EdgePeer {
dev_addr: IpSubnet::new(net_addr, net_bit_len),
sock: RwLock::new(sock.deepcopy()),
_v6_info: RwLock::new(v6_info),
timeout: REGISTER_INTERVAL,
timeout: REGISTER_SUPER_INTERVAL as u8,
last_p2p: AtomicU64::new(0),
last_seen: AtomicU64::new(0),
_last_valid_timestamp: AtomicU64::new(now),

View File

@ -13,6 +13,7 @@ use crate::{
utils::{send_to_sock, Socket},
};
use etherparse::Ethernet2Header;
use num_enum::TryFromPrimitive;
use prost::Message;
use sdlan_sn_rs::utils::BROADCAST_MAC;
use sdlan_sn_rs::{
@ -123,7 +124,15 @@ pub async fn handle_packet(eee: &'static Node, addr: SocketAddr, buf: &[u8]) ->
);
}
if data.is_p2p {
check_peer_registration_needed(eee, !data.is_p2p, src_mac, &None, &from_sock).await;
check_peer_registration_needed(
eee,
!data.is_p2p,
src_mac,
NatType::NoNat,
&None,
&from_sock,
)
.await;
}
handle_tun_packet(eee, &from_sock, !data.is_p2p, data).await;
}
@ -293,7 +302,7 @@ pub async fn handle_packet_peer_info(
if v6_port != 0 {
v6_info = Some(V6Info { port: v6_port, v6 })
}
send_register(eee, &sock, dst_mac, &v6_info).await;
send_register(eee, remote_nat, &sock, dst_mac, &v6_info).await;
// register_with_local_peers(eee).await;
}
@ -451,10 +460,17 @@ async fn handle_packet_register(
return Ok(());
}
let mut remote_nat = NatType::NoNat;
if !from_sn {
info!("[P2P] Rx REGISTER from {}", sender_sock.to_string());
eee.pending_peers.delete_peer_with_mac(&src_mac);
info!(
"[P2P] Rx REGISTER from {}, deleting from pending",
sender_sock.to_string()
);
if let Some((_, v)) = eee.pending_peers.delete_peer_with_mac(&src_mac) {
remote_nat = v.get_nat_type();
}
send_register_ack(eee, origin_sender, &reg).await;
info!("sent back REGISTERACK");
} else {
info!(
"[PsP] Rx REGISTER from {} [{}] to {} via {}",
@ -465,7 +481,7 @@ async fn handle_packet_register(
);
}
// check_peer_registration_needed(eee, from_sn, reg.src_ip, &None, origin_sender).await;
check_peer_registration_needed(eee, from_sn, src_mac, &None, origin_sender).await;
check_peer_registration_needed(eee, from_sn, src_mac, remote_nat, &None, origin_sender).await;
Ok(())
}
@ -523,6 +539,7 @@ pub async fn check_peer_registration_needed(
eee: &'static Node,
from_sn: bool,
src_mac: Mac,
remote_nat: NatType,
_v6_info: &Option<V6Info>,
peer_sock: &SdlanSock,
) {
@ -535,7 +552,9 @@ pub async fn check_peer_registration_needed(
}
match p {
None => {
let _ = register_with_new_peer(eee, from_sn, src_mac, _v6_info, peer_sock).await;
debug!("check peer registration needed, not found in known peers");
let _ = register_with_new_peer(eee, from_sn, src_mac, _v6_info, remote_nat, peer_sock)
.await;
// unimplemented!();
}
Some(k) => {
@ -553,7 +572,7 @@ pub async fn check_peer_registration_needed(
}
let last_seen = k.last_seen.load(Ordering::Relaxed);
// more than 3 seconds
if now - last_seen > 1 {
if now - last_seen > 3 {
check_known_peer_sock_change(eee, from_sn, src_mac, peer_sock, now, ipv4_to_ipv6)
.await;
}
@ -585,7 +604,9 @@ async fn check_known_peer_sock_change(
peersock.to_string()
);
eee.known_peers.delete_peer_with_mac(&mac);
register_with_new_peer(eee, from_sn, mac, &None, peersock).await;
error!("known peers is deleted");
let remote_nat = p.get_nat_type();
register_with_new_peer(eee, from_sn, mac, &None, remote_nat, peersock).await;
} else {
// from sn, sn could see a different sock with us, just ignore it
}
@ -604,6 +625,7 @@ async fn register_with_new_peer(
mac: Mac,
v6_info: &Option<V6Info>,
// dev_addr: &IpSubnet,
remote_nat: NatType,
peersock: &SdlanSock,
) {
let now = get_current_timestamp();
@ -632,10 +654,11 @@ async fn register_with_new_peer(
if eee.config.register_ttl == 1 {
/* We are DMZ host or port is directly accessible. Just let peer to send back the ack */
} else if eee.config.register_ttl > 1 {
/*
let mut alter = 16;
if let Ok(ttl) = eee.udp_sock_v4.ttl() {
let mut temp = peersock.deepcopy();
send_register(eee, &temp, mac, v6_info).await;
send_register(eee, remote_nat, &temp, mac, v6_info).await;
let _ = eee.udp_sock_v4.set_ttl(eee.config.register_ttl as u32);
while alter > 0 {
@ -645,13 +668,15 @@ async fn register_with_new_peer(
}
let _ = eee.udp_sock_v4.set_ttl(ttl);
}
*/
} else {
// Normal STUN
send_register(eee, peersock, mac, v6_info).await;
send_register(eee, remote_nat, peersock, mac, v6_info).await;
}
// 发送给sn
send_register(
eee,
remote_nat,
&eee.config.super_nodes
[eee.config.super_node_index.load(Ordering::Relaxed) as usize],
mac,
@ -660,7 +685,7 @@ async fn register_with_new_peer(
.await;
} else {
// P2P register, send directly
send_register(eee, peersock, mac, v6_info).await;
send_register(eee, remote_nat, peersock, mac, v6_info).await;
}
register_with_local_peers(eee).await;
} else {
@ -675,10 +700,23 @@ async fn register_with_new_peer(
}
async fn register_with_local_peers(eee: &'static Node) {
send_register(eee, &eee.multicast_sock, BROADCAST_MAC, &None).await;
send_register(
eee,
NatType::NoNat,
&eee.multicast_sock,
BROADCAST_MAC,
&None,
)
.await;
}
async fn send_register(eee: &'static Node, sock: &SdlanSock, mac: Mac, _v6_info: &Option<V6Info>) {
async fn send_register(
eee: &'static Node,
remote_nat: NatType,
sock: &SdlanSock,
mac: Mac,
_v6_info: &Option<V6Info>,
) {
if !eee.config.allow_p2p {
debug!("skipping register as p2p is disabled");
return;
@ -715,6 +753,26 @@ async fn send_register(eee: &'static Node, sock: &SdlanSock, mac: Mac, _v6_info:
)
.await;
}
let mut need_guess_port = false;
match self_nat {
NatType::PortRestricted => {
if let NatType::Symmetric = remote_nat {
need_guess_port = true;
}
}
NatType::Symmetric => {
if let NatType::PortRestricted = remote_nat {
need_guess_port = true;
}
}
_other => {}
}
if need_guess_port {
println!("need guess port");
}
/*
let mut target_sock_v4 = sock.deepcopy();
tokio::spawn(async move {
@ -1005,8 +1063,8 @@ fn peer_set_p2p_confirmed(eee: &Node, src_mac: Mac, sender_sock: &SdlanSock) {
"P2P connection established: {} [{}]",
&mac_string, &sock_string,
);
debug!("==> new peer: {} -> {}", &mac_string, &sock_string,);
eee.known_peers.insert_peer(src_mac, scan);
debug!("==> new peer: {} -> {}", &mac_string, &sock_string,);
}
pub async fn check_query_peer_info(eee: &'static Node, mac: Mac) {