Was macht ping -n anders?

Sep 03 2020

Bei der Fehlerbehebung bei einem gelegentlichen Netzwerkstillstand in meinem Heim-Internet bin ich auf diesen technischen Tipp von Dell gestoßen . Sie empfehlen die Verwendung ping -n, um einen durch DNS-Auflösung verursachten Stillstand zu vermeiden. Das brachte mich zum Nachdenken, was macht der -nSchalter eigentlich? Es scheint mir, dass eine DNS-Auflösung erforderlich ist, wenn Sie einen DNS-Namen anpingen, aber nicht, wenn Sie eine IP anpingen.

Über die Manpage:
-n Nur numerische Ausgabe. Es wird kein Versuch unternommen, symbolische Namen nach Hostadressen zu suchen.

Wenn ich eine IP-Adresse anpinge, ping 8.8.8.8wie gibt es hier eine DNS-Suche? Macht ping -n 8.8.8.8etwas anderes?

Antworten

2 KamilMaciorowski Sep 03 2020 at 06:23

Wenn ich eine IP-Adresse anpinge, ping 8.8.8.8wie gibt es hier eine DNS-Suche? Macht ping -n 8.8.8.8etwas anderes?

Dies kann von der Implementierung abhängen. Wenn pingohne -nenthält dns.googlein seinem Ausgang, ping -ntut wohl nicht, das ist der Unterschied. Es ist jedoch möglich, dass keine der Ausgaben die Zeichenfolge enthält.


In meinem Ubuntu 18.04.4 man 8 pinglautet LTS :

pingist Teil des iputilsPakets und die neuesten Versionen sind in Quellform unter verfügbar http://www.skbuff.net/iputils/iputils-current.tar.bz2.

Diese genaue Adresse scheint immer noch nicht zu funktionieren http://www.skbuff.net/iputilsbietet weitere Links, einschließlich des Links zu SourceForge . Ich habe iputils-s20151218 heruntergeladen und den Code gelesen.

-nwird behandelt in ping_common.c:

case 'n':
        options |= F_NUMERIC;
        break;

Dann ist die Option ( options & F_NUMERIC) wichtig in ping.c:

pr_addr(__u32 addr)
{
        …

        if (exiting || (options & F_NUMERIC) ||
            !(hp = gethostbyaddr((char *)&addr, 4, AF_INET)))
                sprintf(buf, "%s", inet_ntoa(*(struct in_addr *)&addr));
        else {
                …

Um dorthin zu gelangen, gethostbyaddrmüssen beide exitingund options & F_NUMERICfalsch sein (da a || bnicht ausgewertet wird, bob dies awahr ist). Letzteres hängt davon ab, ob es verwendet -nwurde oder nicht.

gethostbyaddrist der "Versuch, symbolische Namen nach Hostadressen zu suchen". Siehe man 3 gethostbyaddr. Dies ist derselbe Bibliotheksaufruf, der getent hostsverwendet wird, wenn Sie eine IP-Adresse angeben (siehe man 1 getent).

Sieh den Unterschied:

$ getent hosts 8.8.8.8 8.8.8.8 dns.google $ ping -c 1 dns.google
…
64 bytes from dns.google (8.8.8.8): icmp_seq=1 ttl=120 time=10.6 ms
…
$ ping -n -c 1 dns.google … 64 bytes from 8.8.8.8: icmp_seq=1 ttl=120 time=11.3 ms … $

Es mag scheinen , pingohne -nnur die Zeichenfolge verwendet der Benutzer zur Verfügung gestellt; aber nein:

$ getent hosts poczta.wp.pl 193.17.41.99 poczta.wp.pl $ getent hosts 193.17.41.99
193.17.41.99    poczta.o2.pl
$ ping -c 1 poczta.wp.pl … 64 bytes from poczta.o2.pl (193.17.41.99): icmp_seq=1 ttl=60 time=9.71 ms … $

Hier poczta.wp.plwurde aufgelöst 193.17.41.99und dann 193.17.41.99wurde aufgelöst poczta.o2.pl(Notiz o2statt wp). Die Verwendung von -nwürde den letzteren Schritt unterdrücken.

Bei einigen Adressen geschieht dies:

$ getent hosts superuser.com 151.101.1.69 superuser.com 151.101.193.69 superuser.com 151.101.65.69 superuser.com 151.101.129.69 superuser.com $ getent hosts 151.101.1.69 151.101.193.69 151.101.65.69 151.101.129.69        
$ # the output was empty $ ping -c 1 superuser.com
…
64 bytes from 151.101.1.69 (151.101.1.69): icmp_seq=1 ttl=58 time=37.1 ms
…
$ ping -n -c 1 superuser.com … 64 bytes from 151.101.1.69: icmp_seq=1 ttl=58 time=36.8 ms … $

Aber wenn ich eine numerische Adresse gebe, gibt es keinen Unterschied:

$ getent hosts 8.8.8.8 8.8.8.8 dns.google $ ping -c 1 8.8.8.8
…
64 bytes from 8.8.8.8: icmp_seq=1 ttl=120 time=10.8 ms
…
$ ping -n -c 1 8.8.8.8 … 64 bytes from 8.8.8.8: icmp_seq=1 ttl=120 time=8.91 ms … $ 

Es ist wegen dieses Fragments von ping.c:

if (inet_aton(target, &whereto.sin_addr) == 1) {
        hostname = target;
         if (argc == 1)
                 options |= F_NUMERIC;
} else

inet_atonKonvertiert von der IPv4-Notation für Zahlen und Punkte in eine binäre Form. Es kehrt 1zum Erfolg zurück. Wenn das zuletzt angegebene Argument pingkonvertiert werden kann, wird das Fragment so ausgewertet, options |= F_NUMERIC als ob -nes verwendet wurde .

Ich habe tatsächlich pingaus der Quelle in zwei Versionen kompiliert : das Original und mit if … options |= F_NUMERIC;auskommentiert. Die geänderte Version verhält sich wie folgt:

$ ./ping -c 1 8.8.8.8 … 64 bytes from dns.google (8.8.8.8): icmp_seq=1 ttl=120 time=9.67 ms … $ ./ping -n -c 1 8.8.8.8
…
64 bytes from 8.8.8.8: icmp_seq=1 ttl=120 time=8.69 ms
…
$ 

Jetzt kann ich die Frage explizit beantworten:

Macht ping -n 8.8.8.8etwas anderes [als ping 8.8.8.8]?

Nein. Die Adresse in der IPv4-Notation für Zahlen und Punkte funktioniert ping(unter iputilsLinux) so, als ob sie -nverwendet worden wäre.


Wenn ich eine IP-Adresse anpinge, ping 8.8.8.8wie gibt es hier eine DNS-Suche?

Ich habe einen separaten Netzwerk-Namespace (um sicherzustellen, dass so wenig Verkehr wie möglich stört) mit einem veth-Paar erstellt und dort verwendet wireshark. (Wenn Sie meine Ergebnisse replizieren möchten und Hilfe bei der Prozedur benötigen, lesen Sie diese Antwort , Beispiel 2).

Mit dem Original ping:

  • ping -n -c 1 8.8.8.8erzeugt ICMP echo requestund empfängt ICMP echo reply. Kein DNS beteiligt.
  • ping -c 1 8.8.8.8 macht das gleiche (keine Überraschung hier, oben erklärt).

Dies bedeutet, dass keine DNS-Suche erfolgt . Nachfolgend einige Tests zum Vergleich.

Mit meinem modifizierten ping:

  • ping -n -c 1 8.8.8.8 verhält sich wie das Original.
  • ping -c 1 8.8.8.8fragt den DNS-Server nach ICMP ab und erhält eine Antwort. Das ist zu bekommen dns.google.

Wieder mit dem Original ping:

  • ping -n -c 1 dns.googlefragt den DNS-Server ab und erhält vor ICMP eine Antwort. Dies ist zu übersetzen , dns.googlezu 8.8.8.8oder 8.8.4.4.
  • ping -c 1 dns.googlefragt den DNS-Server ab und erhält eine Antwort vor ICMP (zum Übersetzen in 8.8.8.8oder nach 8.8.4.4) und separat nach ICMP (zum Zurückübersetzen).
1 xenoid Sep 03 2020 at 03:56

Von der Manpage:

-n Nur numerische Ausgabe. Es wird kein Versuch unternommen, symbolische Namen nach Hostadressen zu suchen

Der Unterschied liegt also in der Ausgabe:

>ping  whitehouse.gov
PING whitehouse.gov(g2a02-26f0-0082-02b2-0000-0000-0000-2add.deploy.static.akamaitechnologies.com (2a02:26f0:82:2b2::2add)) 56 data bytes
64 bytes from g2a02-26f0-0082-02b2-0000-0000-0000-2add.deploy.static.akamaitechnologies.com (2a02:26f0:82:2b2::2add): icmp_seq=1 ttl=52 time=7.38 ms
64 bytes from g2a02-26f0-0082-02b2-0000-0000-0000-2add.deploy.static.akamaitechnologies.com (2a02:26f0:82:2b2::2add): icmp_seq=2 ttl=52 time=6.91 ms
64 bytes from g2a02-26f0-0082-02b2-0000-0000-0000-2add.deploy.static.akamaitechnologies.com (2a02:26f0:82:2b2::2add): icmp_seq=3 ttl=52 time=21.6 ms
64 bytes from g2a02-26f0-0082-02b2-0000-0000-0000-2add.deploy.static.akamaitechnologies.com (2a02:26f0:82:2b2::2add): icmp_seq=4 ttl=52 time=7.60 ms
>ping  -n whitehouse.gov
PING whitehouse.gov(2a02:26f0:82:280::2add) 56 data bytes
64 bytes from 2a02:26f0:82:280::2add: icmp_seq=1 ttl=52 time=10.0 ms
64 bytes from 2a02:26f0:82:280::2add: icmp_seq=2 ttl=52 time=5.63 ms
64 bytes from 2a02:26f0:82:280::2add: icmp_seq=3 ttl=52 time=10.4 ms
64 bytes from 2a02:26f0:82:280::2add: icmp_seq=4 ttl=52 time=12.5 ms