Kodėl resolv.conf rodo jūsų VPN DNS, bet užklausos jo nepaiso
Hoste su resolved failas yra vaizdas, o ne būsena. Sekite stub, kiekvienos jungties serverius ir nsswitch eilutę, kad pamatytumėte, ką užklausa iš tikrųjų naudoja.
Žurnaluose niekas neatrodo blogai: sąsaja veikia, sprendiklis praneša VPN DNS serverį, o diske esantis failas jį išvardija. Vis dėlto vidinis pagrindinio kompiuterio vardas vis dar sprendžiamas per vietinį maršrutizatorių. Šie trys teiginiai neprieštarauja vienas kitam, nes failas, kiekvienos jungties būsena ir užklausos kelias yra skirtingi objektai, kurie atsitiktinai turi bendrą vardą. Toliau aprašomas kelias, kurį užklausa iš tikrųjų nueina hoste su systemd-resolved.
Trys objektai, vadinami resolv.conf
Hoste su resolved /etc/resolv.conf paprastai yra simbolinė nuoroda į /run/systemd/resolve/stub-resolv.conf. Tame taikinyje yra vietinio stub klausytojo adresas, 127.0.0.53, ir resolved apskaičiuoti paieškos domenai. Tai būsenos vaizdas, o ne pati būsena.
Būsena gyvena resolved konfigūracijoje kiekvienai jungčiai, todėl resolvectl status gali nesutarti su failu ir vis tiek būti teisus. Kiekviena jungtis neša savo serverius ir savo maršrutizavimo domenus, o stub pasiekia šiuos duomenis, kai ateina užklausa. systemd-resolved vadove aprašomi sugeneruoti failai ir kiekvienos jungties modelis; vaizdo ir būsenos atskyrimas yra ta dalis, kurią verta atsiminti. Pakeitus simbolinės nuorodos taikinį keičiasi tai, ką skaito tradiciniai klientai, o ne tai, ką žino sprendiklis.
Trečias objektas, /run/systemd/resolve/resolv.conf, suploja kiekvieną jungtį į vieną serverių sąrašą. Į tą failą nukreipta programa siunčia užklausas tiesiai į išvardytus serverius ir praleidžia stub, todėl kiekvienos jungties politika jai nebegalioja. Todėl dvi programos toje pačioje mašinoje gali atsakyti į tą patį vardą skirtingai, ir nė viena nėra sugedusi.
Sekite vieną paiešką per NSS
glibc skaito /etc/nsswitch.conf, kad nuspręstų, kas atsako į vardą. hosts eilutė su resolve nukreipia klausimą į nss-resolve, kuris klausia resolved per D-Bus ir gauna kiekvienos jungties atsakymą. Eilutė su vienu files dns siunčia užklausą į adresą, kurį turi /etc/resolv.conf.
Ši viena eilutė paaiškina daugumą nesutarimų tarp naršyklės ir dig. dig skaito resolv.conf tiesiogiai ir niekada neliečia NSS, todėl tikrina stub arba aukštesnį serverį, o ne kelią, kurį naudoja programa. getent hosts internal.example eina per NSS, ir jo atsakymo palyginimas su dig atsakymu yra pirmasis naudingas matavimas.
Programos, kurios turi savo sprendiklį arba kalba DNS per HTTPS su fiksuotu pabaigos tašku, apeina abu kelius. Niekas resolv.conf ar resolved būsenoje jų nevaržo.
Patikrinkite, kam priklauso failas ir kur jis nukreiptas
Perskaitykite nuorodų grandinę prieš ką nors keisdami, nes nuosavybė lemia, kuris failas yra pagrindinis. Kiekviena žemiau esanti komanda tik skaito būseną.
stat -c '%N' /etc/resolv.conf
resolvectl status --no-pager
grep '^hosts' /etc/nsswitch.conf
ls -l /run/systemd/resolve/
Pirmoji eilutė išspausdina nuorodą ir jos taikinį kartu, o paprastas failas, priklausantis VPN scenarijui, reiškia, kad sprendiklis niekada nenagrinėja to įrašo kaip įvesties. Būsenos išvestis išvardija kiekvienos jungties serverius ir maršrutizavimo domenus, kurie nulemia, kur kiekviena užklausa keliauja. nsswitch eilutė pasako, ar stub apskritai klausiamas, todėl stub adresas faile be resolve reiškia, kad užklausos pasiekia vietinį klausytoją, kol niekas nevaldo skaidymo. Paskutinis sąrašas taip pat svarbus, nes hostas be stub-resolv.conf nevykdo čia aprašytos tvarkos.
Jei grandinė baigiasi faile, kurį valdo kitas paketas, VPN klientas ir tas paketas yra du šeimininkai, kuriuos reikia suderinti. Nuorodos pakeitimas išmeta vieno šeimininko darbą ir palieka kito darbą vietoje.
Taisykite pas nuorodos šeimininką
VPN ryšys turėtų registruoti savo serverius ir domenus savo jungtyje, o atsijungus juos atšaukti. NetworkManager resolved integracija ir kliento savas pagalbininkas veikia būtent taip; scenarijus, kuris tik perrašo resolv.conf, to nedaro.
Jau esančioje jungtyje mechanizmą parodo vykdymo metu nustatymai. resolvectl dns tun0 10.40.0.53 prijungia serverį, o resolvectl domain tun0 '~corp.example' prijungia maršrutizavimo domeną. Tildė yra apkrovą nešantis simbolis: ji apriboja tos priesagos užklausas šia jungtimi ir palieka visa kita ramybėje, o ta pati reikšmė be jos tampa paieškos domenu ir skaidymas išgaruoja. Tie adresai yra laboratoriniai pavyzdžiai, o ne nuolatinė konfigūracija. Patvirtinkite su resolvectl query host.corp.example ir perskaitykite, kuri jungtis atsakė.
Registruotam serveriui vis tiek reikia maršruto. Kai užklausa pasiekia tinkamą jungtį ir baigiasi laikas, klaida yra pasiekiamume per tunelį, o ne sprendiklio nuosavybėje.
Kaip atrodo veikianti būsena
Sveikas rezultatas yra nuoseklus visuose trijuose vaizduose: kiekvienos jungties serveriai atitinka tai, ką išdavė VPN, maršrutizavimo domenai apima tik vidines priesagas, o svarbi programa išsprendžia vidinį vardą, tuo tarpu viešas vardas vis dar eina vietiniu keliu. Viena sėkminga užklausa įrodo mažiau nei šis sutarimas.
Tada atjunkite ir pakartokite abi užklausas. Klientas, kuris po išardymo palieka savo domenus registruotus, sukuria mašiną, kuri po kelių valandų nepavyksta vidinėse paieškose, be atviro tunelio ir be akivaizdžios priežasties.