Search code examples
linuxrustxmppsrvsrv-record

SRV lookup request doesn't return an IP address


I am writing an XMPP client. The RFC says I need to connect to the server (like this one) using a SRV query.

When I use the trust_dns_resolver crate to do so, the query seems to be empty. Is this the normal behavior?

use trust_dns_resolver::Resolver;
use trust_dns_resolver::Name;
use std::str::FromStr;

fn main() {
    let resolver = Resolver::from_system_conf().unwrap();
    match resolver.srv_lookup(Name::from_str("_xmpp-client._tcp.xmpp.jp").unwrap()) {
        Ok(response) => {
            for ip in response.ip_iter() {
                println!("{}", ip.to_string());
            }
        },
        Err(e) => println!("{}", e),
    }
}

The dig SRV _xmpp-client._tcp.xmpp.jp command line return the following:

; <<>> DiG 9.16.18 <<>> SRV _xmpp-client._tcp.xmpp.jp
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 16710
;; flags: qr rd ra; QUERY: 1, ANSWER: 3, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
; COOKIE: 2605a5d828b394e22ffbec3e61010461a668fc990570d859 (good)
;; QUESTION SECTION:
;_xmpp-client._tcp.xmpp.jp. IN  SRV

;; ANSWER SECTION:
_xmpp-client._tcp.xmpp.jp. 23   IN  SRV 20 10 5222 sapporo.xmpp.jp.
_xmpp-client._tcp.xmpp.jp. 23   IN  SRV 30 10 5222 gw.lb.xmpp.jp.
_xmpp-client._tcp.xmpp.jp. 23   IN  SRV 10 10 5222 tokyo.xmpp.jp.

;; Query time: 13 msec
;; SERVER: 192.168.1.1#53(192.168.1.1)
;; WHEN: mer. juil. 28 09:16:49 CEST 2021
;; MSG SIZE  rcvd: 183

I will have three IP addresses right ?

I think I'm misunderstanding something, but I don't know what.


Solution

    • It's ok if the SRV lookup return no IP address. in my case, the query return only few tuples composed of a domain name and a port number. After getting them, I have to resolve each one to get its IP address with its port number.

    • The trust_dns_proto crate is mandatory to deal with SRV lookup. So I add it to the Cargo.toml file, and the compiler stop crying...

    Then I can write the following code to extract both port number and domain name:

    use trust_dns_resolver::Resolver;
    use trust_dns_resolver::Name;
    use std::str::FromStr;
    [...]
        let resolver = Resolver::from_system_conf().unwrap();
        match resolver.srv_lookup(Name::from_str("_xmpp-client._tcp.xmpp.jp.").unwrap()) { 
            Ok(response) => {
                for srv in response.iter() {
                    println!("Port number:\t{}", srv.port());
                    println!("Domain name:\t{}\n", srv.target().to_utf8());
                    // have to resolve the domain name here
                }
                println!("{}", response.query().name());
            },
            Err(e) => println!("{}", e),
        }
    

    Thanks to Zeppi. His solution was far from perfect, but it put me on the right track to finding my own.