Diversi mesi fa ho notato che il mio editor di testo (emacs) e IDE (IntelliJ) impiegavano molto tempo per avviarsi. L'ora sembrava variare in base ai server DNS che OS X stava usando.
Sono stato in grado di isolare il problema quando la suite di test di un progetto stava funzionando lentamente. Ho trovato il colpevole (livello superiore) come chiamata a socket.getfqdn()
.
L'esecuzione del seguente comando nel terminale su OS X 10.10.2, dimostra il problema:
$ time python -c 'import socket; socket.getfqdn()'
python -c 'import socket; socket.getfqdn()' 0.02s user 0.00s system 0% cpu 5.122 total
Ho rintracciato il codice che viene eseguito quando viene chiamato socket.getfqdn()
e il ritardo è causato da getaddrinfo(3)
. Ho scritto un piccolo programma che isola il problema e gai_strerror(3)
fornisce questo messaggio:
$ time ./hostinfo
Hostname: MacBook-Pro.local
getaddrinfo: nodename nor servname provided, or not known
./hostinfo 0.00s user 0.00s system 0% cpu 5.101 total
Sembra che il ritardo sia in attesa del timeout della query DNS. I risultati sopra riportati utilizzavano i server DNS pubblici di Google. Se utilizzo i server DNS del mio ISP, tuttavia, il tempo passa a 30 secondi:
$ time python -c 'import socket; socket.getfqdn()'
python -c 'import socket; socket.getfqdn()' 0.01s user 0.01s system 0% cpu 30.114 total
(curiosamente il programma C hostinfo
richiede ancora poco più di 5 secondi)
Che cosa sta causando questo problema? Il mio nome host non è valido o causa problemi?
$ hostname
MacBook-Pro.local
Questo problema non si verifica su un Macbook Air sulla stessa rete.
La principale differenza che posso vedere è che sulla macchina problematica è elencata la confiugrazione DNS seguente:
$ scutil --dns
DNS configuration
resolver #1
search domain[0] : Home
nameserver[0] : 8.8.8.8
nameserver[1] : 8.8.4.4
flags : Request A records
reach : Reachable
DNS configuration (for scoped queries)
resolver #1
search domain[0] : Home
nameserver[0] : 8.8.8.8
nameserver[1] : 8.8.4.4
if_index : 4 (en0)
flags : Scoped, Request A records
reach : Reachable
Sul MacBook Air sono incluse diverse voci aggiuntive relative a mDNS. Ad esempio:
resolver #2
domain : local
options : mdns
timeout : 5
flags : Request A records
order : 300000
Questo sembra essere significativo. È interessante notare che il timeout elencato sopra è all'incirca lo stesso dei runtime sopra.
Devo notare che sono connesso a Internet tramite WiFi e il problema esiste solo quando provo a risolvere il nome host del mio computer.