Czym jest XSS?

05 lipca 2013, 21:52 | Teksty | komentarzy 17
: zin o bezpieczeństwie - pobierz w pdf/epub/mobi.

O błędzie Cross-Site-Scripting napisano już zapewne wiele powieści ;) Podatność ta jest też częstym przedmiotem żartów. Osoby zajmujące się niskopoziomowymi problemami związanymi z bezpieczeństwem mają już czasem po prostu dość zalewu informacji o XSS. Jako świeży przykład może tu posłużyć majowy post Tavisa Omandy na liście fulldisclosure, zdradzający szczegóły błędu 0-day na wszystkie Windowsy:

I guess I’m talking to myself, maybe this list is all about XSS now ;)

Niemniej jednak błąd ten znajduje się na wysokiej, trzeciej pozycji najnowszej edycji dokumentu OWASP Top Ten. Warto w takim razie nieco mu się bliżej przyjrzeć.

Poniższe informacje podane są jedynie w celach edukacyjnych.

Ewentualne testy z wykorzystaniem zamieszczonych tu informacji  należy realizować jedynie na systemach, których bezpieczeństwo możemy oficjalnie sprawdzać.

Istota podatności XSS

Na czym polega istota podatności XSS? Po pierwsze jest to przede wszystkim atak na klienta korzystającego z podatnej webaplikacji (w przeciwieństwie np. do SQL injection, którego głównym celem jest część serwerowa). Po drugie, atak polega na wstrzyknięciu do przeglądarki ofiary fragmentu javascript bądź innego języka skryptowego (np. VBScript), który może być uruchomiony w przeglądarce.

W efekcie, atakujący ma możliwość wykonania dowolnego kodu skryptowego w przeglądarce (nie mylić z uruchomieniem dowolnego kodu w systemie operacyjnym ofiary). W dalszej części tekstu dla uproszczenia będę wspominał tylko o javascript, świadomie pomijając inne możliwości – jak choćby wspomniany vbscript).

Potencjalne skutki wykorzystania

Czym może skutkować wykonanie kodu javascript w przeglądarce ofiary? Warto tu wspomnieć takie możliwości:

  • wykradanie cookies (w tym cookies sesyjnych) – tj. de facto przejęcie (zalogowanej) sesji ofiary,
  • dynamiczna podmiany zawartości strony www (np. słynne „this site have beed hacked”),
  • uruchomienie keyloggera w przeglądarce,
  • hostowanie malware-u z wykorzystaniem zaatakowanej aplikacji (np. poprzez użycie tagu iframe).

Swoją drogą, istnieje sporo narzędzi, które w praktyce pokazują różne możliwe negatywne efekty wykorzystania XSS.

Podział błędów XSS

Błędy XSS dzielimy na trzy kategorie:

  • Persistent (inna spotykana nazwa: stored) XSS – najbardziej złowroga odmiana, polegająca na umieszczeniu kodu javascript po stronie serwerowej (stąd nazwa – stored). Przykładowo,  atakujący umieszcza javascript w komentarzu pod postem na blogu (np. komentując ten post ;) a komentarz automatycznie jest wysyłany do moderacji. W momencie kiedy moderator odczytuje komentarz, uruchamiany jest automatycznie javascript, który może wykradać cookie sesyjne administratora. W tym momencie atakujący ma dostęp do zalogowanej sesji administracyjnej bez znajomości użytkownika oraz hasła! Taka historia zresztą miała miejsce już spory czas temu w systemie WordPress, gdzie udało mi się zlokalizować dokładnie taką lukę :-)
  • Reflected XSS – w tym przypadku kod javascript zaszyty jest w linku, który atakujący przesyła do ofiary. Ofiara po kliknięciu na linka łączy się z aplikacją, przekazując jej nieświadomie fragment HTML zawierający kod wykonujący javascript.  Aplikacja zwraca ofierze (stąd nazwa: reflected) wynik (tj. HTML) zawierający wcześniej podany javascript, powodując wykonanie kodu w przeglądarce.
  • DOM Based XSS – rzadziej spotykana postać – opisana tutaj.

Praktyczny przykład

Zobaczmy całość na prostym przykładzie (reflected XSS):

xss

Zielonej ofierze podsyłany jest tutaj link z przykazaniem parametru do aplikacji. Parametr search zawiera wstrzyknięcie javascriptu tagiem <script>. Zobaczmy co dzieje się dalej:

xss2

Całość można prześledzić na realnej aplikacji, dostępnej tutaj (czy nie ostrzegałem przed klikaniem „w ciemno”? ;-)

Wyżej widzieliśmy bardzo prosty przykład uruchomienia javascriptu poprzez tag <script>. W jaki sposób wykonać javascript jedynie poprzez odpowiednie manipulacje parametrami do tagu? Na przykład tak:

Zresztą najrozmaitszych metod jest naprawdę wiele.

Metody ochrony przed XSS

W jaki sposób chronić się przed XSS? Przede wszystkim w odpowiedni sposób filtrować dane przesyłane przez użytkownika – przed ich wyświetleniem w aplikacji. Najczęściej przybiera to formę zamiany pewnych istotnych znaków kontrolnych HTML (głównie mam tu na myśli znaki otwierające / zamykające tagi oraz atrybuty tagu) na encje HTML:

Taka filtracja najprawdopodobniej zlikwiduje większość podatności XSS w naszej aplikacji. Warto jednak wspomnieć, że wskazana powyżej metoda ochrony w pewnych przypadkach nie działa – odsyłam tutaj do wcześniej wspomnianego XSS Prevention Cheat Sheet i bardziej złożonych przypadków opisanych w tym dokumencie. W każdym razie, realizacja odpowiedniego filtrowania w złożonej aplikacji nie jest wcale taka prosta jakby się mogło wydawać (stąd też duża liczba aplikacji jest podatna).

Jeszcze inną i zazwyczaj niewiele kosztującą metodą ochrony przed jednym z efektów XSS – tj. wykradaniem cookies – jest zastosowanie parametru HttpOnly dla ciastek sesyjnych.

Konkretne technologie posiadają również własne mechanizmy ochronne – jak choćby request validation w .net.

Pewna ochrona może być równolegle realizowana po stronie klienckiej – jako przykład może służyć dodatek NoScript do Firefoxa, czy wręcz wbudowane w przeglądarki mechanizmy ochrony przed XSS.

Czas na ćwiczenie:

1. Szczegóły statków tutaj mają możliwość wyświetlenia obrazu silnika.

2. Bazując na tej funkcjonalności, przygotuj linka realizującego reflected XSS (np. wyświetlenie popupu javascriptowego z tekstem: XSS).

3. Wystarczy że javascript uruchomi się dla przeglądarki Firefox (idealnie – również dla innych przeglądarek).

4. Jeśli chcesz sprawdzić czy przygotowany przez Ciebie XSS jest poprawny w kontekście tego zadania – wyświetl w popupie ciasteczka (document.cookie).

Odpowiedzi podsyłajcie na adres: sekurak@sekurak.pl z tytułem: hackme XSS.

Nie zapomnijcie podesłać linka do hackme znajomym ;-)
Zapraszam też do naszego poprzedniego hackme – tematyka SQL injection.

— michal.sajdak<at>securitum.pl

 

Spodobał Ci się wpis? Podziel się nim ze znajomymi:



Komentarze

  1. SebaVegas

    proste, a są jakieś nagrody ?

    Odpowiedz
    • Raczej całość dla sportu, nagrodą jest satysfakcja :-) Czy proste? Kwestia gustu, ale na razie mam tylko jedną w pełni prawidłową odpowiedź (przypominam, XSS trzeba znaleźć w miejscu gdzie wyświetlane są szczegóły silnika statu, a nie w dowolnym miejscu tej aplikacji)
      –ms

      Odpowiedz
  2. Michał B

    Trudne faktycznie nie było, pewnie dlatego, że miałem już styczność z podobną sytuacją.

    Ciekawsze było zmodyfikowanie payloadu tak, by działał też na innych przeglądarkach niż Firefox. :)

    Odpowiedz
  3. fuzzy

    Ciekawe, chociaż rzeczywiście dość proste :).

    Fajnie że kontynuowany jest wątek „UFO” w hackme ;).

    Odpowiedz
  4. Jolka

    To może podzielicie się rozwiązaniem? Bo mnie te nawiasy pokonały :(

    Odpowiedz
    • Na razie nie…bo to zepsuje zabawę tym którzy chcą jeszcze powalczyć.
      Jak ktoś prześle choćby częściową poprawną odpowiedź, i poprosi o pełną wersję – wtedy podeślę ;-)
      –ms

      Odpowiedz
  5. marcin

    Dobra Firefox jest, jeszcze reszta przegladarek teraz pewnie zacznie sie jazda :D

    Odpowiedz
  6. lz

    Czy można prosić o więcej podpowiedzi ? Nie mam pomysłu jak obejść tą zamianę na &lt – jakieś inne kodowanie ? No i nie wiem czy aby na pewno mam się wbijać w <img src=…" Poprosimy! ;)

    Odpowiedz
  7. Krzychu

    Czy jest jakakolwiek szansa na to, że pojawi się rozwiązanie (ew. podpowiedzi)? Zastanawiam się w jaki sposób trzeba się za to zabrać, a nie jestem jeszcze zbyt biegły w tym temacie : )

    Odpowiedz
    • Kukaj na sekuraka – jest taka szansa. Szczególnie że niedługo kolejne hackme.

      Odpowiedz
  8. Mariusz

    Hej,

    A możecie opisać DOM XSS, bo czytam to co jest napisane na OWASP i nie widzę różnicy z stored XSS (może to kwestia języka)

    Odpowiedz
  9. FL3SH

    „udało mi się zlokalizować” <– link is down ;)

    Odpowiedz
  10. Damian

    Hej,

    Czy ktoś może napisać podpowiedź? Męczę się z tym i nie mogę ominąć problemu z nawiasami. Wnioskuję, że element o który trzeba zahaczyć XSS to atrybut onerror lub onload w tagu img prawda?

    Odpowiedz
  11. Kowal

    jakś może podpowiedź

    Odpowiedz
  12. Przemek

    działa to jeszcze? na chromie już chyba nie da się tego zrobić inaczej niż poprzez zewnętrzny skrypt

    Odpowiedz

Odpowiedz na sekurak