feat: added test tcp client
This commit is contained in:
parent
e5f6c2aa7e
commit
35bcf5352b
125
Cargo.lock
generated
125
Cargo.lock
generated
@ -86,6 +86,15 @@ version = "1.0.75"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "a4668cab20f66d8d020e1fbc0ebe47217433c1b6c8f2040faf858554e394ace6"
|
checksum = "a4668cab20f66d8d020e1fbc0ebe47217433c1b6c8f2040faf858554e394ace6"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "atomic-polyfill"
|
||||||
|
version = "0.1.11"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "e3ff7eb3f316534d83a8a2c3d1674ace8a5a71198eba31e2e2b597833f699b28"
|
||||||
|
dependencies = [
|
||||||
|
"critical-section",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "atty"
|
name = "atty"
|
||||||
version = "0.2.14"
|
version = "0.2.14"
|
||||||
@ -237,6 +246,12 @@ version = "0.2.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "dcb25d077389e53838a8158c8e99174c5a9d902dee4904320db714f3c653ffba"
|
checksum = "dcb25d077389e53838a8158c8e99174c5a9d902dee4904320db714f3c653ffba"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "critical-section"
|
||||||
|
version = "1.1.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "7059fff8937831a9ae6f0fe4d658ffabf58f2ca96aa9dec1c889f936f705f216"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "crypto-mac"
|
name = "crypto-mac"
|
||||||
version = "0.10.1"
|
version = "0.10.1"
|
||||||
@ -269,6 +284,38 @@ dependencies = [
|
|||||||
"zeroize",
|
"zeroize",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "defmt"
|
||||||
|
version = "0.3.5"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "a8a2d011b2fee29fb7d659b83c43fce9a2cb4df453e16d441a51448e448f3f98"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 1.3.2",
|
||||||
|
"defmt-macros",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "defmt-macros"
|
||||||
|
version = "0.3.6"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "54f0216f6c5acb5ae1a47050a6645024e6edafc2ee32d421955eccfef12ef92e"
|
||||||
|
dependencies = [
|
||||||
|
"defmt-parser",
|
||||||
|
"proc-macro-error",
|
||||||
|
"proc-macro2 1.0.66",
|
||||||
|
"quote 1.0.33",
|
||||||
|
"syn 2.0.29",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "defmt-parser"
|
||||||
|
version = "0.3.3"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "269924c02afd7f94bc4cecbfa5c379f6ffcf9766b3408fe63d22c728654eccd0"
|
||||||
|
dependencies = [
|
||||||
|
"thiserror",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "derive_more"
|
name = "derive_more"
|
||||||
version = "0.14.1"
|
version = "0.14.1"
|
||||||
@ -277,7 +324,7 @@ checksum = "6d944ac6003ed268757ef1ee686753b57efc5fcf0ebe7b64c9fc81e7e32ff839"
|
|||||||
dependencies = [
|
dependencies = [
|
||||||
"proc-macro2 0.4.30",
|
"proc-macro2 0.4.30",
|
||||||
"quote 0.6.13",
|
"quote 0.6.13",
|
||||||
"rustc_version",
|
"rustc_version 0.2.3",
|
||||||
"syn 0.15.44",
|
"syn 0.15.44",
|
||||||
]
|
]
|
||||||
|
|
||||||
@ -561,6 +608,28 @@ version = "0.28.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0"
|
checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "hash32"
|
||||||
|
version = "0.2.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "b0c35f58762feb77d74ebe43bdbc3210f09be9fe6742234d573bacc26ed92b67"
|
||||||
|
dependencies = [
|
||||||
|
"byteorder",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "heapless"
|
||||||
|
version = "0.7.16"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "db04bc24a18b9ea980628ecf00e6c0264f3c1426dac36c00cb49b6fbad8b0743"
|
||||||
|
dependencies = [
|
||||||
|
"atomic-polyfill",
|
||||||
|
"hash32",
|
||||||
|
"rustc_version 0.4.0",
|
||||||
|
"spin",
|
||||||
|
"stable_deref_trait",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "heck"
|
name = "heck"
|
||||||
version = "0.3.3"
|
version = "0.3.3"
|
||||||
@ -657,6 +726,12 @@ dependencies = [
|
|||||||
"cfg-if",
|
"cfg-if",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "managed"
|
||||||
|
version = "0.8.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "0ca88d725a0a943b096803bd34e73a4437208b6077654cc4ecb2947a5f91618d"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "memchr"
|
name = "memchr"
|
||||||
version = "2.5.0"
|
version = "2.5.0"
|
||||||
@ -1022,7 +1097,16 @@ version = "0.2.3"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a"
|
checksum = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"semver",
|
"semver 0.9.0",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "rustc_version"
|
||||||
|
version = "0.4.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
|
||||||
|
dependencies = [
|
||||||
|
"semver 1.0.18",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@ -1053,6 +1137,12 @@ dependencies = [
|
|||||||
"semver-parser",
|
"semver-parser",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "semver"
|
||||||
|
version = "1.0.18"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "b0293b4b29daaf487284529cc2f5675b8e57c61f70167ba415a463651fd6a918"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "semver-parser"
|
name = "semver-parser"
|
||||||
version = "0.7.0"
|
version = "0.7.0"
|
||||||
@ -1155,6 +1245,21 @@ version = "1.11.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "62bb4feee49fdd9f707ef802e22365a35de4b7b299de4763d44bfea899442ff9"
|
checksum = "62bb4feee49fdd9f707ef802e22365a35de4b7b299de4763d44bfea899442ff9"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "smoltcp"
|
||||||
|
version = "0.10.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "8d2e3a36ac8fea7b94e666dfa3871063d6e0a5c9d5d4fec9a1a6b7b6760f0229"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 1.3.2",
|
||||||
|
"byteorder",
|
||||||
|
"cfg-if",
|
||||||
|
"defmt",
|
||||||
|
"heapless",
|
||||||
|
"libc",
|
||||||
|
"managed",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "socket2"
|
name = "socket2"
|
||||||
version = "0.5.3"
|
version = "0.5.3"
|
||||||
@ -1222,6 +1327,21 @@ dependencies = [
|
|||||||
"pcap-sys",
|
"pcap-sys",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "spin"
|
||||||
|
version = "0.9.8"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67"
|
||||||
|
dependencies = [
|
||||||
|
"lock_api",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "stable_deref_trait"
|
||||||
|
version = "1.2.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "strsim"
|
name = "strsim"
|
||||||
version = "0.8.0"
|
version = "0.8.0"
|
||||||
@ -1301,6 +1421,7 @@ dependencies = [
|
|||||||
"packets",
|
"packets",
|
||||||
"pcap-sys",
|
"pcap-sys",
|
||||||
"rand 0.8.5",
|
"rand 0.8.5",
|
||||||
|
"smoltcp",
|
||||||
"tokio",
|
"tokio",
|
||||||
"tokio-stream",
|
"tokio-stream",
|
||||||
]
|
]
|
||||||
|
|||||||
@ -170,7 +170,9 @@ pub fn get_macs_and_src_for_ip(
|
|||||||
0
|
0
|
||||||
};
|
};
|
||||||
|
|
||||||
let Ok(dst_addr): Result<Ipv4Addr, _> = (&dst).try_into() else { return false };
|
let Ok(dst_addr): Result<Ipv4Addr, _> = (&dst).try_into() else {
|
||||||
|
return false;
|
||||||
|
};
|
||||||
let dst_addr: u32 = dst_addr.into();
|
let dst_addr: u32 = dst_addr.into();
|
||||||
|
|
||||||
(mask & dst_addr) == (mask & ip_int)
|
(mask & dst_addr) == (mask & ip_int)
|
||||||
@ -181,7 +183,12 @@ pub fn get_macs_and_src_for_ip(
|
|||||||
#[cfg(debug_assertions)]
|
#[cfg(debug_assertions)]
|
||||||
{
|
{
|
||||||
for link in links.iter() {
|
for link in links.iter() {
|
||||||
println!("Link {}: {:?} ({})", link.name(), link.addr(), link.ifindex());
|
println!(
|
||||||
|
"Link {}: {:?} ({})",
|
||||||
|
link.name(),
|
||||||
|
link.addr(),
|
||||||
|
link.ifindex()
|
||||||
|
);
|
||||||
|
|
||||||
println!("\tAddrs:");
|
println!("\tAddrs:");
|
||||||
for addr in addrs.iter().filter(|addr| addr.ifindex() == link.ifindex()) {
|
for addr in addrs.iter().filter(|addr| addr.ifindex() == link.ifindex()) {
|
||||||
@ -191,7 +198,11 @@ pub fn get_macs_and_src_for_ip(
|
|||||||
}
|
}
|
||||||
|
|
||||||
println!("\tNeighbors:");
|
println!("\tNeighbors:");
|
||||||
for neigh in neighs.iter().filter(|neigh| neigh.ifindex() == link.ifindex()) {
|
for neigh in neighs
|
||||||
|
.iter()
|
||||||
|
.filter(|neigh| neigh.ifindex() == link.ifindex())
|
||||||
|
{
|
||||||
|
println!("\t\ttest {:?}, {:?}", neigh.ifindex(), neigh.dst());
|
||||||
println!("\t\t{:?}, {:?}", neigh.dst(), neigh.lladdr());
|
println!("\t\t{:?}, {:?}", neigh.dst(), neigh.lladdr());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -224,7 +235,9 @@ pub fn get_neigh_for_addr(
|
|||||||
addr: &Addr,
|
addr: &Addr,
|
||||||
) -> Option<(Ipv4Addr, Link, [u8; 6])> {
|
) -> Option<(Ipv4Addr, Link, [u8; 6])> {
|
||||||
for link in links.iter() {
|
for link in links.iter() {
|
||||||
let Some(neigh) = link.get_neigh(&neighs, addr) else { continue; };
|
let Some(neigh) = link.get_neigh(&neighs, addr) else {
|
||||||
|
continue;
|
||||||
|
};
|
||||||
return Some((addr.try_into().ok()?, link, neigh));
|
return Some((addr.try_into().ok()?, link, neigh));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -239,7 +252,7 @@ pub fn get_neigh_for_addr(
|
|||||||
};
|
};
|
||||||
|
|
||||||
let Some(first_hop) = def_neigh.hop_iter().next() else {
|
let Some(first_hop) = def_neigh.hop_iter().next() else {
|
||||||
return None
|
return None;
|
||||||
};
|
};
|
||||||
|
|
||||||
if n.ifindex() != first_hop.ifindex() {
|
if n.ifindex() != first_hop.ifindex() {
|
||||||
@ -322,8 +335,12 @@ impl Addr {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Determines the type of data in [`Addr::hw_address`]
|
// Determines the type of data in [`Addr::hw_address`]
|
||||||
pub fn atype(&self) -> c_int {
|
pub fn atype(&self) -> Option<c_int> {
|
||||||
unsafe { nl_addr_get_family(self.addr) }
|
if self.addr.is_null() {
|
||||||
|
None
|
||||||
|
} else {
|
||||||
|
Some(unsafe { nl_addr_get_family(self.addr) })
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns the length of the subnet mask applying to this address
|
/// Returns the length of the subnet mask applying to this address
|
||||||
@ -334,8 +351,8 @@ impl Addr {
|
|||||||
|
|
||||||
impl Debug for Addr {
|
impl Debug for Addr {
|
||||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
match self.atype() {
|
let res = match self.atype() {
|
||||||
AF_INET => {
|
Some(AF_INET) => {
|
||||||
let octets = self.hw_address();
|
let octets = self.hw_address();
|
||||||
f.debug_struct("Addr")
|
f.debug_struct("Addr")
|
||||||
.field(
|
.field(
|
||||||
@ -351,7 +368,7 @@ impl Debug for Addr {
|
|||||||
)
|
)
|
||||||
.finish()
|
.finish()
|
||||||
}
|
}
|
||||||
AF_LLC => {
|
Some(AF_LLC) => {
|
||||||
let octets = self.hw_address();
|
let octets = self.hw_address();
|
||||||
|
|
||||||
f.debug_struct("Addr")
|
f.debug_struct("Addr")
|
||||||
@ -359,22 +376,23 @@ impl Debug for Addr {
|
|||||||
"addr",
|
"addr",
|
||||||
&format!(
|
&format!(
|
||||||
"{:02X?}:{:02X?}:{:02X?}:{:02X?}:{:02X?}:{:02X?}",
|
"{:02X?}:{:02X?}:{:02X?}:{:02X?}:{:02X?}:{:02X?}",
|
||||||
octets[0],
|
octets[0], octets[1], octets[2], octets[3], octets[4], octets[5],
|
||||||
octets[1],
|
),
|
||||||
octets[2],
|
|
||||||
octets[3],
|
|
||||||
octets[4],
|
|
||||||
octets[5],
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
.finish()
|
.finish()
|
||||||
}
|
}
|
||||||
|
None => f
|
||||||
|
.debug_struct("Addr")
|
||||||
|
.field("addr", &"unknown")
|
||||||
|
.field("atype", &"unknown")
|
||||||
|
.finish(),
|
||||||
_ => f
|
_ => f
|
||||||
.debug_struct("Addr")
|
.debug_struct("Addr")
|
||||||
.field("addr", &self.hw_address())
|
.field("addr", &self.hw_address())
|
||||||
.field("atype", &self.atype())
|
.field("atype", &self.atype())
|
||||||
.finish(),
|
.finish(),
|
||||||
}
|
};
|
||||||
|
res
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -551,7 +569,9 @@ pub fn get_srcip_for_dstip(routes: &Cache<Route>, ip: Ipv4Addr) -> Option<Ipv4Ad
|
|||||||
0
|
0
|
||||||
};
|
};
|
||||||
|
|
||||||
let Ok(dst_addr): Result<Ipv4Addr, _> = (&dst).try_into() else { return false };
|
let Ok(dst_addr): Result<Ipv4Addr, _> = (&dst).try_into() else {
|
||||||
|
return false;
|
||||||
|
};
|
||||||
let dst_addr: u32 = dst_addr.into();
|
let dst_addr: u32 = dst_addr.into();
|
||||||
|
|
||||||
(mask & dst_addr) == (mask & ip_int)
|
(mask & dst_addr) == (mask & ip_int)
|
||||||
|
|||||||
@ -290,6 +290,61 @@ impl<'a> TCPPkt<'a> {
|
|||||||
pub fn data(&self) -> &[u8] {
|
pub fn data(&self) -> &[u8] {
|
||||||
&self.data[(self.len() as usize)..]
|
&self.data[(self.len() as usize)..]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn verify_checksum<I1, I2>(&self, srcip: I1, dstip: I2) -> bool
|
||||||
|
where
|
||||||
|
I1: Into<Ipv4Addr>,
|
||||||
|
I2: Into<Ipv4Addr>,
|
||||||
|
{
|
||||||
|
let source = srcip.into();
|
||||||
|
let dest = dstip.into();
|
||||||
|
|
||||||
|
let protocol = &[0x00u8, 0x06u8];
|
||||||
|
|
||||||
|
let tcp_length = (self.data.len()) as u16;
|
||||||
|
|
||||||
|
let len: u8 = (self.len()).try_into().unwrap();
|
||||||
|
let len = len << 4;
|
||||||
|
|
||||||
|
let bytes = [
|
||||||
|
&source.octets()[..],
|
||||||
|
&dest.octets(),
|
||||||
|
protocol,
|
||||||
|
&tcp_length.to_be_bytes(),
|
||||||
|
&self.srcport().to_be_bytes()[..],
|
||||||
|
&self.dstport().to_be_bytes(),
|
||||||
|
&self.seqnumber().to_be_bytes(),
|
||||||
|
&self.acknumber().to_be_bytes(),
|
||||||
|
&[len],
|
||||||
|
&[self.flags()],
|
||||||
|
&self.window().to_be_bytes(),
|
||||||
|
&[0, 0],
|
||||||
|
&self.urgent_ptr().to_be_bytes(),
|
||||||
|
&self.options(),
|
||||||
|
&self.data(),
|
||||||
|
]
|
||||||
|
.concat();
|
||||||
|
|
||||||
|
let checksum = bytes
|
||||||
|
.chunks(2)
|
||||||
|
.map(|pair| {
|
||||||
|
if pair.len() == 1 {
|
||||||
|
(pair[0] as u32) << 8
|
||||||
|
} else {
|
||||||
|
(pair[0] as u32) << 8 | (pair[1] as u32)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.fold(0u32, |acc, e| acc + e)
|
||||||
|
+ 30;
|
||||||
|
// + 30 to intentionally deviate from
|
||||||
|
// the RFC, to make it so that I can identify the packets as sparse
|
||||||
|
// packets
|
||||||
|
|
||||||
|
let checksum = (checksum >> 16) + (checksum & 0xffff);
|
||||||
|
let checksum = ((checksum >> 16) as u16) + (checksum as u16);
|
||||||
|
|
||||||
|
checksum == self.checksum()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
@ -590,35 +645,3 @@ impl TCPPacketBuilder {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(test)]
|
|
||||||
mod test {
|
|
||||||
use std::net::Ipv4Addr;
|
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn test_tcp_checksum() {
|
|
||||||
let srcip = Ipv4Addr::new(127, 0, 0, 1);
|
|
||||||
let dstip = srcip.clone();
|
|
||||||
|
|
||||||
let packet = super::TCPPacketBuilder::default()
|
|
||||||
.srcport(36916)
|
|
||||||
.dstport(54248)
|
|
||||||
.seqnumber(0xFD65_CA26)
|
|
||||||
.syn(true)
|
|
||||||
.window(65495)
|
|
||||||
.options(vec![
|
|
||||||
0x02, 0x04, 0xff, 0xd7, 0x04, 0x02, 0x08, 0x0a, 0xce, 0x4e, 0xad, 0x04, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x01, 0x03, 0x03, 0x07,
|
|
||||||
])
|
|
||||||
.build(srcip, dstip, vec![]);
|
|
||||||
|
|
||||||
assert_eq!(
|
|
||||||
&packet.data,
|
|
||||||
&vec![
|
|
||||||
0x90, 0x34, 0xd3, 0xe8, 0xfd, 0x65, 0xca, 0x26, 0x00, 0x00, 0x00, 0x00, 0xa0, 0x02,
|
|
||||||
0xff, 0xd7, 0xfe, 0x30, 0x00, 0x00, 0x02, 0x04, 0xff, 0xd7, 0x04, 0x02, 0x08, 0x0a,
|
|
||||||
0xce, 0x4e, 0xad, 0x04, 0x00, 0x00, 0x00, 0x00, 0x01, 0x03, 0x03, 0x07
|
|
||||||
]
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@ -255,7 +255,7 @@ impl<T: Activated> Interface<T> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_filter(
|
pub fn set_filter(
|
||||||
&mut self,
|
&self,
|
||||||
filter: &str,
|
filter: &str,
|
||||||
optimize: bool,
|
optimize: bool,
|
||||||
mask: Option<u32>,
|
mask: Option<u32>,
|
||||||
|
|||||||
@ -13,3 +13,4 @@ rand = "0.8.5"
|
|||||||
tokio = { version = "1.32.0", features = ["full"] }
|
tokio = { version = "1.32.0", features = ["full"] }
|
||||||
anyhow = "1.0.75"
|
anyhow = "1.0.75"
|
||||||
tokio-stream = { version = "0.1.14", features = ["full"] }
|
tokio-stream = { version = "0.1.14", features = ["full"] }
|
||||||
|
smoltcp = { version = "0.10.0", default-features = false, features = ["socket-tcp", "phy-raw_socket", "std", "async", "medium-ethernet"] }
|
||||||
|
|||||||
@ -1,13 +1,11 @@
|
|||||||
use std::net::Ipv4Addr;
|
use std::{net::Ipv4Addr, sync::Arc};
|
||||||
|
|
||||||
use anyhow::anyhow;
|
use anyhow::anyhow;
|
||||||
|
|
||||||
use nl_sys::{netlink, route};
|
use nl_sys::{netlink, route};
|
||||||
use packets::EthernetPacket;
|
use packets::{
|
||||||
|
EthernetPacket, IPv4Packet, Layer3Packet, Layer4Packet, TCPPacketBuilder, UDPPacket,
|
||||||
struct TcpConnection {
|
};
|
||||||
packets_to_ack: Vec<EthernetPacket>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[tokio::main]
|
#[tokio::main]
|
||||||
async fn main() -> anyhow::Result<()> {
|
async fn main() -> anyhow::Result<()> {
|
||||||
@ -17,7 +15,7 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
.ok_or(anyhow!("could not get target IP"))?
|
.ok_or(anyhow!("could not get target IP"))?
|
||||||
.parse::<Ipv4Addr>()?;
|
.parse::<Ipv4Addr>()?;
|
||||||
|
|
||||||
let (ifname, src_mac, dst_mac, srcip) = {
|
let (ifname, srcip, src_mac, dst_mac) = {
|
||||||
let socket = netlink::Socket::new()?;
|
let socket = netlink::Socket::new()?;
|
||||||
|
|
||||||
let routes = socket.get_routes()?;
|
let routes = socket.get_routes()?;
|
||||||
@ -25,13 +23,12 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
let links = socket.get_links()?;
|
let links = socket.get_links()?;
|
||||||
let addrs = socket.get_addrs()?;
|
let addrs = socket.get_addrs()?;
|
||||||
|
|
||||||
let (ifname, srcip, srcmac, dstmac) =
|
|
||||||
route::get_macs_and_src_for_ip(&addrs, &routes, &neighs, &links, ip)
|
route::get_macs_and_src_for_ip(&addrs, &routes, &neighs, &links, ip)
|
||||||
.ok_or(anyhow!("unable to find a route to the IP"))?;
|
.ok_or(anyhow!("unable to find a route to the IP"))?
|
||||||
|
|
||||||
(ifname, srcip, srcmac, dstmac)
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
dbg!((&ifname, srcip, src_mac, dst_mac));
|
||||||
|
|
||||||
let mut interface = pcap_sys::Interface::<pcap_sys::DevDisabled>::new(&ifname)?;
|
let mut interface = pcap_sys::Interface::<pcap_sys::DevDisabled>::new(&ifname)?;
|
||||||
|
|
||||||
interface.set_buffer_size(8192)?;
|
interface.set_buffer_size(8192)?;
|
||||||
@ -39,7 +36,7 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
interface.set_promisc(false)?;
|
interface.set_promisc(false)?;
|
||||||
interface.set_timeout(10)?;
|
interface.set_timeout(10)?;
|
||||||
|
|
||||||
let mut interface = interface.activate()?;
|
let interface = Arc::new(interface.activate()?);
|
||||||
|
|
||||||
let port: u16 = loop {
|
let port: u16 = loop {
|
||||||
let port = rand::random();
|
let port = rand::random();
|
||||||
@ -48,7 +45,29 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let packets_to_ack: Vec<EthernetPacket> = vec![];
|
||||||
|
|
||||||
interface.set_filter(&format!("inbound and tcp port {}", port), true, None)?;
|
interface.set_filter(&format!("inbound and tcp port {}", port), true, None)?;
|
||||||
|
|
||||||
|
let seq: u32 = rand::random();
|
||||||
|
|
||||||
|
let udppacket = UDPPacket::construct(port, 54248, vec![]);
|
||||||
|
|
||||||
|
let tcppacket = TCPPacketBuilder::default()
|
||||||
|
.srcport(port)
|
||||||
|
.dstport(54248)
|
||||||
|
.seqnumber(seq)
|
||||||
|
.acknumber(0)
|
||||||
|
.syn(true)
|
||||||
|
.window(65495)
|
||||||
|
.build(srcip.clone(), ip.clone(), vec![]);
|
||||||
|
|
||||||
|
let ippacket = IPv4Packet::construct(srcip, ip, &Layer4Packet::UDP(udppacket));
|
||||||
|
let ethpacket = EthernetPacket::construct(src_mac, dst_mac, &Layer3Packet::IPv4(ippacket));
|
||||||
|
|
||||||
|
println!("sending packet...");
|
||||||
|
|
||||||
|
interface.sendpacket(ethpacket.pkt())?;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user