Skip to main content

rusthound_ce/modules/resolver/
resolv.rs

1use log::{info,debug};
2use colored::Colorize;
3
4use trust_dns_resolver::TokioAsyncResolver;
5use trust_dns_resolver::config::*;
6
7use std::net::{IpAddr,Ipv4Addr,SocketAddr};
8use std::collections::HashMap;
9use std::time::Duration;
10use crate::objects::computer::Computer;
11
12/// Function to resolve all IP address from the LDAP FQDN vector
13/// <https://docs.rs/trust-dns-resolver/latest/trust_dns_resolver/index.html>
14/// <https://github.com/shadowsocks/shadowsocks-rust/blob/master/crates/shadowsocks-service/src/config.rs>
15pub async fn resolving_all_fqdn(
16   dns_tcp:       bool,
17   name_server:   &String,
18   fqdn_ip:       &mut HashMap<String, String>,
19   vec_computer:  &[Computer]
20) {
21   info!("Resolving FQDN to IP address started...");
22   for value in fqdn_ip.to_owned()
23   {
24      for i in 0..vec_computer.len()
25      {
26         if (*vec_computer[i].properties().name() == value.0.to_owned()) 
27         && (*vec_computer[i].properties().enabled()) {
28            debug!("Trying to resolve FQDN: {}",value.0.to_string());
29            // Resolve FQDN to IP address
30            let address = resolver(value.0.to_string(),dns_tcp,name_server).await;
31            if let Some(addr) = address {
32               fqdn_ip.insert(value.0.to_owned().to_string(),addr.to_owned().to_string());
33               info!("IP address for {}: {}",&value.0.to_string().yellow().bold(),&addr.yellow().bold());
34            }
35         }
36         continue
37      }
38   }
39   info!("Resolving FQDN to IP address finished!");
40}
41
42/// Asynchronous function to resolve IP address from the ldap FQDN
43pub async fn resolver(
44   fqdn: String,
45   dns_tcp: bool, 
46   name_server: &String,
47) -> Option<String>
48{
49   // Get configuration and options for resolver
50   let (c,o) = make_resolver_conf(dns_tcp,name_server);
51
52   // Construct a new Resolver with default configuration options
53   let resolver = TokioAsyncResolver::tokio(c,o);
54
55   // Resolver
56   let result = resolver.lookup_ip(fqdn);
57
58   match result.await{
59      Ok(response) => {
60         let address = response.iter().next().expect("no addresses returned!");
61         if address.is_ipv4() {
62            return Some(address.to_string())
63         }
64      }
65      Err(_err) => {},
66   };
67   None
68}
69
70/// Function to prepare resolver configuration
71pub fn make_resolver_conf(
72   dns_tcp: bool, 
73   name_server: &String,
74) -> (ResolverConfig,ResolverOpts) {
75   let mut c = ResolverConfig::new();
76   let mut socket = SocketAddr::new(IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)), 53);
77   let mut dns_protocol = Protocol::Udp;
78   if dns_tcp
79   {
80      dns_protocol = Protocol::Tcp;
81   }
82   if !name_server.contains("127.0.0.1") {
83      let address = name_server.parse::<IpAddr>().unwrap_or(std::net::IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)));
84      socket.set_ip(address);
85   }
86
87   debug!("Protocol DNS: {:?}",&dns_protocol);
88   debug!("Name server DNS: {:?}",name_server.parse::<Ipv4Addr>());
89
90   c.add_name_server(NameServerConfig {
91      socket_addr: socket,
92      protocol: dns_protocol,
93      tls_dns_name: None,
94      trust_negative_responses: false,
95      bind_addr: None,
96   });
97
98   let mut o = ResolverOpts::default();
99   o.timeout = Duration::new(0, 10);
100   (c,o)
101}