įvedimas
Šiuolaikinės įmonių turinio filtravimo sistemos iš tokių žinomų gamintojų kaip Cisco, BlueCoat, FireEye turi gana daug bendro su galingesniais analogais – DPI sistemomis, kurios aktyviai diegiamos nacionaliniu lygiu. Abiejų darbo esmė – patikrinti įeinantį ir išeinantį interneto srautą ir, remiantis juodaisiais/baltaisiais sąrašais, priimti sprendimą uždrausti interneto ryšį. Ir kadangi abu savo darbo pagrindus remiasi panašiais principais, jų apėjimo metodai taip pat turės daug bendro.
Viena iš technologijų, leidžiančių gana efektyviai apeiti tiek DPI, tiek korporacines sistemas, yra domeno sąsajos technologija. Jo esmė ta, kad mes einame į užblokuotą šaltinį, pasislėpdami už kito, geros reputacijos viešo domeno, kurio, aišku, neužblokuos jokia sistema, pavyzdžiui, google.com.
Apie šią technologiją jau parašyta nemažai straipsnių ir pateikta daug pavyzdžių. Tačiau populiarios ir neseniai aptartos DNS-over-HTTPS ir šifruoto SNI technologijos, taip pat nauja TLS 1.3 protokolo versija leidžia apsvarstyti kitą domeno fronto variantą.
Technologijos supratimas
Pirma, apibrėžkime šiek tiek pagrindines sąvokas, kad visi suprastų, kas yra kas ir kodėl viso to reikia. Paminėjome eSNI mechanizmą, kurio veikimas bus aptartas toliau. eSNI (šifruoto serverio pavadinimo indikacijos) mechanizmas yra saugi SNI versija, prieinama tik TLS 1.3 protokolui. Pagrindinė idėja yra užšifruoti, be kita ko, informaciją apie tai, į kurį domeną siunčiama užklausa.
Dabar pažiūrėkime, kaip eSNI mechanizmas veikia praktiškai.
Tarkime, kad turime interneto šaltinį, kurį blokuoja modernus DPI sprendimas (paimkime, pavyzdžiui, garsųjį torrent tracker rutracker.nl). Kai bandome pasiekti torrent stebėjimo priemonės svetainę, matome standartinį teikėjo stulpelį, nurodantį, kad išteklius užblokuotas:
RKN svetainėje šis domenas iš tikrųjų yra įtrauktas į sustojimo sąrašus:
Kai pateikiate užklausą whois, galite pamatyti, kad pats domenas yra „paslėptas“ už debesų tiekėjo „Cloudflare“.
Tačiau skirtingai nei RKN „specialistai“, labiau techniškai išmanantys „Beeline“ darbuotojai (arba mokomi karčios mūsų garsaus reguliuotojo patirties) ne kvailai uždraudė svetainę pagal IP adresą, o įtraukė domeno pavadinimą į sustabdymo sąrašą. Tai galite lengvai patikrinti, jei pažiūrėsite, kokie kiti domenai yra paslėpti po tuo pačiu IP adresu, apsilankykite viename iš jų ir pamatysite, ar prieiga nėra užblokuota:
Kaip tai atsitinka? Kaip teikėjo DPI žino, kuriame domene yra mano naršyklė, nes visi ryšiai vyksta naudojant https protokolą, o mes dar nepastebėjome, kad „Beeline“ pakeistų https sertifikatus? Ar jis aiškiaregis, ar aš sekamas?
Pabandykime atsakyti į šį klausimą žiūrėdami į srautą per wireshark
Ekrano kopija rodo, kad pirmiausia naršyklė gauna serverio IP adresą per DNS, tada įvyksta standartinis TCP rankos paspaudimas su paskirties serveriu, o tada naršyklė bando užmegzti SSL ryšį su serveriu. Norėdami tai padaryti, jis siunčia SSL Client Hello paketą, kuriame yra šaltinio domeno pavadinimas aiškiu tekstu. Šis laukas reikalingas „Cloudflare“ sąsajos serveriui, kad būtų tinkamai nukreiptas ryšys. Čia tiekėjas DPI užklumpa mus, nutraukdamas ryšį. Tuo pačiu metu iš teikėjo negauname jokio pranešimo ir matome standartinę naršyklės klaidą, tarsi svetainė būtų išjungta arba tiesiog neveikia:
Dabar įgalinkime eSNI mechanizmą naršyklėje, kaip parašyta instrukcijose
Norėdami tai padaryti, atidarome „Firefox“ konfigūracijos puslapį about: config ir suaktyvinkite šiuos nustatymus:
network.trr.mode = 2;
network.trr.uri = https://mozilla.cloudflare-dns.com/dns-query
network.security.esni.enabled = true
Po to patikrinsime, ar „Cloudflare“ svetainėje nustatymai veikia tinkamai.
Voila. Mūsų mėgstamiausia sekimo priemonė atidaryta be jokių VPN ar tarpinių serverių. Dabar pažiūrėkime į eismo sąvartyną Wireshark, kad pamatytume, kas atsitiko.
Šį kartą ssl kliento „hello“ pakete nėra aiškiai nurodytas paskirties domenas, o vietoje to pakete atsirado naujas laukas - encrypted_server_name - čia yra rutracker.nl reikšmė, ir tik „Cloudflare frontend“ serveris gali tai iššifruoti. lauke. Ir jei taip, tada teikėjas DPI neturi kito pasirinkimo, kaip nusiplauti rankas ir leisti tokį srautą. Kitų šifravimo parinkčių nėra.
Taigi, pažiūrėjome, kaip ši technologija veikia naršyklėje. Dabar pabandykime tai pritaikyti konkretesniems ir įdomesniems dalykams. Ir pirmiausia mes išmokysime tą patį garbaną naudoti eSNI darbui su TLS 1.3, ir tuo pat metu pamatysime, kaip veikia pats eSNI pagrįstas domeno frontas.
Domeno frontavimas naudojant eSNI
Atsižvelgiant į tai, kad curl naudoja standartinę openssl biblioteką, kad prisijungtų per https protokolą, pirmiausia turime ten suteikti eSNI palaikymą. „Openssl“ pagrindiniuose filialuose eSNI palaikymo dar nėra, todėl turime atsisiųsti specialų openssl filialą, jį sukompiliuoti ir įdiegti.
Mes klonuojame saugyklą iš GitHub ir kompiliuojame kaip įprasta:
$ git clone https://github.com/sftcd/openssl
$ cd openssl
$ ./config
$ make
$ cd esnistuff
$ make
Tada mes klonuojame saugyklą su curl ir sukonfigūruojame jos kompiliavimą naudodami mūsų sudarytą openssl biblioteką:
$ cd $HOME/code
$ git clone https://github.com/niallor/curl.git curl-esni
$ cd curl-esni
$ export LD_LIBRARY_PATH=/opt/openssl
$ ./buildconf
$ LDFLAGS="-L/opt/openssl" ./configure --with-ssl=/opt/openssl --enable-esni --enable-debug
Čia svarbu teisingai nurodyti visus katalogus, kuriuose yra openssl (mūsų atveju tai yra /opt/openssl/) ir įsitikinti, kad konfigūravimo procesas vyksta be klaidų.
Jei konfigūracija sėkminga, pamatysime eilutę:
ĮSPĖJIMAS: esni ESNI įjungtas, bet pažymėtas EKSPERIMENTINIS. Naudokite atsargiai!
$ make
Sėkmingai sukūrę paketą, mes naudosime specialų bash failą iš openssl konfigūruoti ir paleisti curl. Patogumui nukopijuokime jį į katalogą su curl:
cp /opt/openssl/esnistuff/curl-esni
ir pateikti bandomąją https užklausą „Cloudflare“ serveriui, tuo pačiu metu įrašydami DNS ir TLS paketus „Wireshark“.
$ ESNI_COVER="www.hello-rkn.ru" ./curl-esni https://cloudflare.com/
Serverio atsakyme, be daug derinimo informacijos iš openssl ir curl, iš „Cloudflare“ gausime HTTP atsakymą su kodu 301.
HTTP/1.1 301 Moved Permanently
< Date: Sun, 03 Nov 2019 13:12:55 GMT
< Transfer-Encoding: chunked
< Connection: keep-alive
< Cache-Control: max-age=3600
< Expires: Sun, 03 Nov 2019 14:12:55 GMT
< Location: https://www.cloudflare.com/
tai rodo, kad mūsų užklausa buvo sėkmingai pristatyta į paskirties serverį, išklausyta ir apdorota.
Dabar pažiūrėkime į „wireshark“ eismo sąvartyną, t.y. ką šiuo atveju matė teikėjas DPI.
Matyti, kad curl pirmiausia kreipėsi į DNS serverį dėl viešojo eSNI rakto, skirto cloudflare serveriui – TXT DNS užklausa adresu _esni.cloudflare.com (paketas Nr. 13). Tada, naudodama openssl biblioteką, curl išsiuntė TLS 1.3 užklausą į „Cloudflare“ serverį, kurioje SNI laukas buvo užšifruotas viešuoju raktu, gautu atliekant ankstesnį veiksmą (22 paketas). Tačiau, be eSNI lauko, SSL-hello pakete taip pat buvo laukas su įprastu - atviru SNI, kurį galime nurodyti bet kokia tvarka (šiuo atveju -
Į šį atvirą SNI lauką jokiu būdu nebuvo atsižvelgta, kai jį apdorojo „Cloudflare“ serveriai, ir jis buvo naudojamas tik kaip teikėjo DPI kaukė. „Cloudflare“ serveris gavo mūsų ssl-hello paketą, iššifravo eSNI, iš ten ištraukė originalų SNI ir apdorojo jį taip, lyg nieko nebūtų nutikę (kurdamas eSNI darė viską tiksliai taip, kaip planuota).
Vienintelis dalykas, kurį šiuo atveju galima pagauti DPI požiūriu, yra pirminė DNS užklausa _esni.cloudflare.com. Tačiau DNS užklausą atidarėme tik norėdami parodyti, kaip šis mechanizmas veikia iš vidaus.
Norėdami pagaliau ištraukti kilimėlį iš po DPI, naudojame jau minėtą DNS-over-HTTPS mechanizmą. Mažas paaiškinimas – DOH yra protokolas, leidžiantis apsisaugoti nuo „man-in-the-middle“ atakos siunčiant DNS užklausą per HTTPS.
Vykdykime užklausą dar kartą, bet šį kartą viešuosius eSNI raktus gausime per https protokolą, o ne DNS:
ESNI_COVER="www.hello-rkn.ru" DOH_URL=https://mozilla.cloudflare-dns.com/dns-query ./curl-esni https://cloudflare.com/
Užklausos srauto išmetimas parodytas toliau esančioje ekrano kopijoje:
Galima pastebėti, kad curl pirmiausia pasiekia mozilla.cloudflare-dns.com serverį per DoH protokolą (https ryšys su serveriu 104.16.249.249), kad gautų iš jų SNI šifravimo viešųjų raktų reikšmes, o tada į paskirties vietą. serveris, slepiasi už domeno
Be aukščiau nurodyto DoH sprendiklio mozilla.cloudflare-dns.com, galime naudotis ir kitomis populiariomis DoH paslaugomis, pavyzdžiui, iš garsiosios blogio korporacijos.
Vykdykime šią užklausą:
ESNI_COVER="www.kremlin.ru" DOH_URL=https://dns.google/dns-query ./curl-esni https://rutracker.nl/
Ir mes gauname atsakymą:
< HTTP/1.1 301 Moved Permanently
< Date: Sun, 03 Nov 2019 14:10:22 GMT
< Content-Type: text/html
< Transfer-Encoding: chunked
< Connection: keep-alive
< Set-Cookie: __cfduid=da0144d982437e77b0b37af7d00438b1a1572790222; expires=Mon, 02-Nov-20 14:10:22 GMT; path=/; domain=.rutracker.nl; HttpOnly; Secure
< Location: https://rutracker.nl/forum/index.php
< CF-Cache-Status: DYNAMIC
< Expect-CT: max-age=604800, report-uri="https://report-uri.cloudflare.com/cdn-cgi/beacon/expect-ct"
< Server: cloudflare
< CF-RAY: 52feee696f42d891-CPH
Šiuo atveju kreipėmės į užblokuotą rutracker.nl serverį, naudodami DoH solver dns.google (čia nėra rašybos klaidos, dabar garsioji korporacija turi savo pirmojo lygio domeną) ir prisidengėme kitu domenu, kuris yra griežtai uždrausta visiems DPI blokuoti mirties skausmu. Remdamiesi gautu atsakymu galite suprasti, kad mūsų užklausa buvo sėkmingai apdorota.
Kaip papildomą patikrinimą, ar teikėjo DPI reaguoja į atvirą SNI, kurį perduodame kaip priedangą, galime pateikti užklausą rutracker.nl, prisidengiant kokiu nors kitu draudžiamu šaltiniu, pavyzdžiui, kitu „geru“ torrento sekikliu:
$ ESNI_COVER="rutor.info" DOH_URL=https://dns.google/dns-query ./curl-esni https://rutracker.nl/
Atsakymo iš serverio negausime, nes... mūsų užklausą blokuos DPI sistema.
Trumpa pirmosios dalies išvada
Taigi, mes galėjome pademonstruoti eSNI funkcionalumą naudodami openssl ir curl ir išbandyti domeno frontingo veikimą, pagrįstą eSNI. Lygiai taip pat galime pritaikyti savo mėgstamus įrankius, naudojančius openssl biblioteką, kad jie veiktų „pasidangstydami“ kitais domenais. Daugiau informacijos apie tai kituose mūsų straipsniuose.
Šaltinis: www.habr.com