pub mod tcp{
use pnet::packet::{tcp::{MutableTcpPacket, TcpFlags::{ACK, SYN}, TcpPacket,TcpOption,},Packet,ipv4::Ipv4Packet};
use pnet::datalink::{NetworkInterface,channel,Channel::Ethernet};
use pnet::packet::ethernet::{EtherTypes, EthernetPacket};
use pnet::packet::ip::IpNextHeaderProtocols::Tcp;
use pnet::transport::{transport_channel,TransportChannelType::Layer4};
use pnet::transport::TransportProtocol::Ipv4;
use std::sync::mpsc;
use std::thread::{sleep, spawn};
use std::net::{IpAddr,Ipv4Addr};
use std::time::Duration;
use crate::util::util::get_local_ip;
pub fn make_tcp_packet(tcp: &mut MutableTcpPacket){
tcp.set_flags(SYN);
tcp.set_window(1000); tcp.set_data_offset(6);
tcp.set_sequence(20);
tcp.set_acknowledgement(100);
tcp.set_options(&[TcpOption::mss(1460)]); }
pub fn send_recv_packet(tcp: &mut MutableTcpPacket,remote_addr: Ipv4Addr,interface: NetworkInterface)->bool{
let (mut tx, _) = transport_channel(4096, Layer4(Ipv4(Tcp))).unwrap();
let lp = tcp.get_source().clone();
let rp = tcp.get_destination().clone();
let (t, r) = mpsc::channel();
let handle = spawn(move || {
t.send(match recv(interface, lp,rp, get_local_ip().unwrap().0,remote_addr) {
Err(e) => {
eprintln!("[Error] {:?}", e);
0u8
}
Ok(flags) => flags,
})
.unwrap();
});
sleep(Duration::from_millis(10));
tx.send_to(tcp.to_immutable(), IpAddr::V4(remote_addr)).unwrap();
match r.recv_timeout(Duration::from_millis(1000)) {
Err(_) => {
return false;
},
Ok(f) => {
handle.join().unwrap();
if f == SYN+ACK {
return true;
}else{
return false;
}
}
}
}
fn recv(
interface: NetworkInterface,
lp: u16,
rp: u16,
li: Ipv4Addr,
ri: Ipv4Addr,
) -> Result<u8, ()> {
let mut flags = 0u8;
if let Ethernet(_, mut rx) = channel(&interface, Default::default()).unwrap() {
loop {
let bytes = rx.next().unwrap();
let frame = EthernetPacket::new(bytes);
if frame.is_none() {
continue;
}
let frame = frame.unwrap();
if frame.get_ethertype() != EtherTypes::Ipv4 {
continue;
}
let ipv4 = Ipv4Packet::new(frame.payload());
if ipv4.is_none() {
continue;
}
let ipv4 = ipv4.unwrap();
if ipv4.get_source() != ri || ipv4.get_destination() != li {
continue;
}
if ipv4.get_next_level_protocol() != Tcp {
continue;
}
let tcp = TcpPacket::new(ipv4.payload());
if tcp.is_none() {
continue;
}
let tcp = tcp.unwrap();
if tcp.get_source() != rp || tcp.get_destination() != lp {
continue;
}
flags = tcp.get_flags();
break; }
}
Ok(flags)
}
}