r_lanlib/scanners/
full_scanner.rs1use derive_builder::Builder;
4use std::{
5 sync::{Arc, mpsc},
6 thread::JoinHandle,
7 time::Duration,
8};
9
10use crate::{
11 error::Result,
12 network::NetworkInterface,
13 targets::{ips::IPTargets, ports::PortTargets},
14 wire::{DEFAULT_PACKET_SEND_TIMING, Wire},
15};
16
17use super::{
18 Device, ScanMessage, Scanner, arp_scanner::ARPScanner,
19 syn_scanner::SYNScanner,
20};
21
22#[derive(Builder)]
24#[builder(setter(into))]
25pub struct FullScanner {
26 interface: Arc<NetworkInterface>,
28 wire: Wire,
30 targets: Arc<IPTargets>,
32 ports: Arc<PortTargets>,
34 vendor: bool,
36 host: bool,
38 idle_timeout: Duration,
40 #[builder(default = DEFAULT_PACKET_SEND_TIMING)]
43 throttle: Duration,
44 notifier: mpsc::Sender<ScanMessage>,
46 source_port: u16,
48}
49
50impl FullScanner {
51 pub fn builder() -> FullScannerBuilder {
53 FullScannerBuilder::default()
54 }
55
56 fn get_syn_targets_from_arp_scan(&self) -> Result<Vec<Device>> {
57 let (tx, rx) = mpsc::channel::<ScanMessage>();
58
59 let mut syn_targets: Vec<Device> = Vec::new();
60
61 let arp = ARPScanner::builder()
62 .interface(Arc::clone(&self.interface))
63 .wire(self.wire.clone())
64 .targets(Arc::clone(&self.targets))
65 .source_port(self.source_port)
66 .include_vendor(self.vendor)
67 .include_host_names(self.host)
68 .idle_timeout(self.idle_timeout)
69 .throttle(self.throttle)
70 .notifier(tx.clone())
71 .build()?;
72
73 arp.scan()?;
74
75 loop {
76 if let Ok(msg) = rx.recv() {
77 match msg {
78 ScanMessage::Done => {
79 log::debug!("arp sending complete");
80 break;
81 }
82 ScanMessage::ARPScanDevice(device) => {
83 syn_targets.push(device.to_owned());
84 }
85 _ => {}
86 }
87 }
88 }
89
90 Ok(syn_targets)
91 }
92}
93
94impl Scanner for FullScanner {
96 fn scan(&self) -> Result<JoinHandle<Result<()>>> {
97 let syn_targets = self.get_syn_targets_from_arp_scan()?;
98
99 let syn = SYNScanner::builder()
100 .interface(Arc::clone(&self.interface))
101 .wire(self.wire.clone())
102 .targets(syn_targets)
103 .ports(Arc::clone(&self.ports))
104 .source_port(self.source_port)
105 .idle_timeout(self.idle_timeout)
106 .throttle(self.throttle)
107 .notifier(self.notifier.clone())
108 .build()?;
109
110 syn.scan()
111 }
112}
113
114#[cfg(test)]
115#[path = "./full_scanner_tests.rs"]
116mod tests;