1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
pub mod ip_adapter_info;
pub mod ip_adapter_info_list;
pub mod ip_addr_string;
pub use crate::{
ip_adapter_info::IpAdapterInfo,
ip_adapter_info_list::IpAdapterInfoList,
ip_addr_string::IpAddrString,
};
use std::{
convert::TryInto,
io::Error as IoError,
net::Ipv4Addr,
};
use winapi::{
ctypes::c_void,
shared::{
ntdef::{
PULONG,
ULONG,
},
winerror::NO_ERROR,
},
um::iphlpapi::SendARP,
};
pub fn get_adapters_info() -> std::io::Result<IpAdapterInfoList> {
IpAdapterInfoList::get()
}
pub fn send_arp(dest_ip: Ipv4Addr, src_ip: Option<Ipv4Addr>) -> Result<(u64, ULONG), IoError> {
let mut mac_addr = std::u64::MAX;
let mut mac_addr_len: ULONG = 6;
let ret = unsafe {
SendARP(
u32::from_ne_bytes(dest_ip.octets()),
u32::from_ne_bytes(src_ip.map(|ip| ip.octets()).unwrap_or([0; 4])),
&mut mac_addr as *mut u64 as *mut c_void,
&mut mac_addr_len as PULONG,
)
};
if ret == NO_ERROR {
Ok((mac_addr, mac_addr_len))
} else {
Err(IoError::from_raw_os_error(ret.try_into().unwrap()))
}
}