Cookies Hacking

Nauka hakowania AWS od zera do bohatera z htARTE (HackTricks AWS Red Team Expert)!

Inne sposoby wsparcia HackTricks:

Grupa Try Hard Security


Ciasteczka posiadają kilka atrybutów kontrolujących ich zachowanie w przeglądarce użytkownika. Oto przegląd tych atrybutów w bardziej biernym tonie:

Wygaśnięcie i Max-Age

Datę wygaśnięcia ciasteczka określa atrybut Expires. Z kolei atrybut Max-age definiuje czas w sekundach do momentu usunięcia ciasteczka. Wybierz Max-age, ponieważ odzwierciedla on bardziej nowoczesne praktyki.

Domena

Hosty, które mają otrzymać ciasteczko, są określone przez atrybut Domain. Domyślnie jest on ustawiony na host, który wydał ciasteczko, nie obejmując jego subdomen. Jednak gdy atrybut Domain jest jawnie ustawiony, obejmuje on również subdomeny. Sprawia to, że określenie atrybutu Domain jest mniej restrykcyjną opcją, przydatną w scenariuszach, gdzie konieczne jest udostępnianie ciasteczek między subdomenami. Na przykład ustawienie Domain=mozilla.org sprawia, że ciasteczka są dostępne na jego subdomenach, takich jak developer.mozilla.org.

Ścieżka

Konkretna ścieżka URL, która musi być obecna w żądanym URL-u, aby został wysłany nagłówek Cookie, jest wskazana przez atrybut Path. Ten atrybut traktuje znak / jako separator katalogów, umożliwiając dopasowania w podkatalogach.

Zasady kolejności

Gdy dwa ciasteczka mają tę samą nazwę, wybór ciasteczka do wysłania opiera się na:

  • Ciasteczko pasujące do najdłuższej ścieżki w żądanym URL-u.

  • Najnowsze ciasteczko, jeśli ścieżki są identyczne.

SameSite

  • Atrybut SameSite określa, czy ciasteczka są wysyłane w żądaniach pochodzących z domen zewnętrznych. Oferuje trzy ustawienia:

  • Strict: Ogranicza wysyłanie ciasteczka w żądaniach zewnętrznych.

  • Lax: Pozwala na wysyłanie ciasteczka wraz z żądaniami GET inicjowanymi przez strony zewnętrzne.

  • None: Umożliwia wysyłanie ciasteczka z dowolnej domeny zewnętrznej.

Pamiętaj, że podczas konfigurowania ciasteczek zrozumienie tych atrybutów może pomóc w zapewnieniu, że zachowują się one zgodnie z oczekiwaniami w różnych scenariuszach.

Typ żądania

Przykładowy kod

Wysyłane ciasteczka, gdy

Link

<a href="..."></a>

NotSet*, Lax, None

Prerender

<link rel="prerender" href=".."/>

NotSet*, Lax, None

Form GET

<form method="GET" action="...">

NotSet*, Lax, None

Form POST

<form method="POST" action="...">

NotSet*, None

iframe

<iframe src="..."></iframe>

NotSet*, None

AJAX

$.get("...")

NotSet*, None

Obraz

<img src="...">

NetSet*, None

Tabela z Invicti i nieco zmodyfikowana. Ciasteczko z atrybutem SameSite pomoże zmniejszyć ataki CSRF, gdy wymagana jest zalogowana sesja.

*Zauważ, że od Chrome 80 (luty/2019) domyślne zachowanie ciasteczka bez atrybutu samesite będzie luźne (https://www.troyhunt.com/promiscuous-cookies-and-their-impending-death-via-the-samesite-policy/). Zauważ, że tymczasowo, po zastosowaniu tej zmiany, ciasteczka bez polityki SameSite w Chrome będą traktowane jako None podczas pierwszych 2 minut, a następnie jako Lax dla żądań POST z najwyższego poziomu między witrynami.

Flagi Ciasteczek

HttpOnly

Zapobiega to klientowi dostępu do ciasteczka (na przykład za pomocą Javascript np. document.cookie)

Ominięcia

  • Jeśli strona wysyła ciasteczka jako odpowiedź na żądania (na przykład na stronie PHPinfo), możliwe jest wykorzystanie XSS do wysłania żądania do tej strony i ukradzenia ciasteczek z odpowiedzi (sprawdź przykład w https://hackcommander.github.io/posts/2022/11/12/bypass-httponly-via-php-info-page/.

  • Można to ominąć za pomocą żądań HTTP TRACE jako odpowiedź serwera (jeśli ta metoda HTTP jest dostępna) odzwierciedli wysłane ciasteczka. Ta technika nazywa się Śledzenie Międzywitrynne.

  • Ta technika jest unikana przez nowoczesne przeglądarki, które nie zezwalają na wysyłanie żądania TRACE z JS. Jednak znaleziono pewne sposoby obejścia tego w określonym oprogramowaniu, takie jak wysyłanie \r\nTRACE zamiast TRACE do IE6.0 SP2.

  • Innym sposobem jest wykorzystanie podatności zero/dnia przeglądarek.

  • Możliwe jest nadpisanie ciasteczek HttpOnly poprzez przeprowadzenie ataku przepełnienia schowka ciasteczkowego:

pageCookie Jar Overflow

Secure

Żądanie tylko wyśle ciasteczko w żądaniu HTTP, jeśli żądanie jest przesyłane przez bezpieczny kanał (zazwyczaj HTTPS).

Prefiksy Ciasteczek

Ciasteczka z prefiksem __Secure- muszą być ustawione razem z flagą secure na stronach zabezpieczonych protokołem HTTPS.

Dla ciasteczek z prefiksem __Host- muszą być spełnione kilka warunków:

  • Muszą być ustawione z flagą secure.

  • Muszą pochodzić z strony zabezpieczonej protokołem HTTPS.

  • Nie wolno im określać domeny, co uniemożliwia ich przesyłanie do subdomen.

  • Ścieżka dla tych ciasteczek musi być ustawiona na /.

Ważne jest zauważenie, że ciasteczka z prefiksem __Host- nie mogą być wysyłane do naddomen ani subdomen. To ograniczenie pomaga w izolowaniu ciasteczek aplikacji. Dlatego stosowanie prefiksu __Host- dla wszystkich ciasteczek aplikacji można uznać za dobrą praktykę w celu poprawy bezpieczeństwa i izolacji.

Nadpisywanie ciasteczek

Więc jedną z ochron __Host- prefiksowanych ciasteczek jest zapobieganie ich nadpisywaniu z subdomen. Zapobieganie na przykład atakom Cookie Tossing. W prezentacji Cookie Crumbles: Unveiling Web Session Integrity Vulnerabilities (paper) przedstawiono, że było możliwe ustawienie ciasteczek z prefiksem __HOST- z subdomeny, oszukując parser, na przykład dodając "=" na początku lub na początku i na końcu...:

Albo w PHP było możliwe dodanie innych znaków na początku nazwy ciasteczka, które miały zostać zamienione na podkreślenia, umożliwiając nadpisanie ciasteczek __HOST-:

Ataki na Ciasteczka

Jeśli niestandardowe ciasteczko zawiera wrażliwe dane, sprawdź je (szczególnie jeśli bierzesz udział w CTF), ponieważ może być podatne na ataki.

Dekodowanie i Manipulowanie Ciasteczkami

Wrażliwe dane osadzone w ciasteczkach powinny zawsze być dokładnie sprawdzane. Ciasteczka zakodowane w Base64 lub podobnych formatach często mogą być zdekodowane. Ta podatność pozwala atakującym zmieniać zawartość ciasteczka i podszywać się pod innych użytkowników, kodując zmodyfikowane dane z powrotem do ciasteczka.

Przechwycenie Sesji

Ten atak polega na kradzieży ciasteczka użytkownika w celu uzyskania nieautoryzowanego dostępu do jego konta w aplikacji. Korzystając z ukradzionego ciasteczka, atakujący może podszyć się pod prawowitego użytkownika.

Ustalanie Sesji

W tym scenariuszu atakujący oszukuje ofiarę, aby użyła określonego ciasteczka do zalogowania się. Jeśli aplikacja nie przypisuje nowego ciasteczka po zalogowaniu, atakujący, posiadając oryginalne ciasteczko, może podszyć się pod ofiarę. Ta technika polega na tym, że ofiara loguje się za pomocą ciasteczka dostarczonego przez atakującego.

Jeśli znalazłeś XSS w subdomenie lub masz kontrolę nad subdomeną, przeczytaj:

pageCookie Tossing

Ofiarowanie Sesji

Tutaj atakujący przekonuje ofiarę do użycia ciasteczka sesji atakującego. Ofiara, wierząc, że jest zalogowana do swojego konta, nieumyślnie wykonuje czynności w kontekście konta atakującego.

Jeśli znalazłeś XSS w subdomenie lub masz kontrolę nad subdomeną, przeczytaj:

pageCookie Tossing

Kliknij w poprzedni link, aby uzyskać dostęp do strony wyjaśniającej możliwe wady JWT.

Tokeny JSON Web (JWT) używane w ciasteczkach mogą również zawierać podatności. Aby uzyskać szczegółowe informacje na temat potencjalnych wad i jak je wykorzystać, zaleca się zapoznanie się z podlinkowanym dokumentem dotyczącym hakowania JWT.

Podrobienie Żądania Międzywitrynowego (CSRF)

Ten atak zmusza zalogowanego użytkownika do wykonania niechcianych działań w aplikacji internetowej, w której obecnie jest uwierzytelniony. Atakujący mogą wykorzystać ciasteczka, które są automatycznie wysyłane z każdym żądaniem do podatnej strony.

Puste Ciasteczka

(Sprawdź dalsze szczegóły w oryginalnym badaniu) Przeglądarki pozwalają na tworzenie ciasteczek bez nazwy, co można zademonstrować za pomocą JavaScriptu, jak pokazano poniżej:

document.cookie = "a=v1"
document.cookie = "=test value;" // Setting an empty named cookie
document.cookie = "b=v2"

Wynikiem w nagłówku cookie wysłanym jest a=v1; test value; b=v2;. Co ciekawe, pozwala to na manipulowanie ciasteczkami, jeśli ustawiono puste ciasteczko z nazwą, potencjalnie kontrolując inne ciasteczka poprzez ustawienie pustego ciasteczka na określoną wartość:

function setCookie(name, value) {
document.cookie = `${name}=${value}`;
}

setCookie("", "a=b"); // Setting the empty cookie modifies another cookie's value

Chrome Bug: Problem z kodowym punktem zastępczym Unicode

W Chrome, jeśli punkt kodowy zastępczy Unicode jest częścią ustawionego ciasteczka, document.cookie ulega uszkodzeniu, zwracając później pusty ciąg znaków:

document.cookie = "\ud800=meep";

To prowadzi do tego, że document.cookie zwraca pusty ciąg znaków, wskazując na trwałe uszkodzenie.

Przemyt ciasteczek z powodu problemów z parsowaniem

(Sprawdź szczegóły w oryginalnym badaniu) Kilka serwerów internetowych, w tym te z Javy (Jetty, TomCat, Undertow) i Pythona (Zope, cherrypy, web.py, aiohttp, bottle, webob), źle obsługuje ciasteczka ze względu na przestarzałe wsparcie dla RFC2965. Odczytują wartość ciasteczka w podwójnych cudzysłowach jako pojedynczą wartość, nawet jeśli zawiera średniki, które normalnie powinny oddzielać pary klucz-wartość:

RENDER_TEXT="hello world; JSESSIONID=13371337; ASDF=end";

Wrażliwości na Wstrzykiwanie Ciasteczek

(Sprawdź dalsze szczegóły w oryginalnym badaniu) Nieprawidłowe parsowanie ciasteczek przez serwery, w szczególności Undertow, Zope oraz te korzystające z http.cookie.SimpleCookie i http.cookie.BaseCookie w Pythonie, tworzy możliwości ataków wstrzykiwania ciasteczek. Te serwery niepoprawnie ograniczają początek nowych ciasteczek, pozwalając atakującym na podszywanie się pod ciasteczka:

  • Undertow oczekuje nowego ciasteczka natychmiast po wartości w cudzysłowiu bez średnika.

  • Zope szuka przecinka, aby rozpocząć parsowanie kolejnego ciasteczka.

  • Klasy ciasteczek w Pythonie zaczynają parsowanie od znaku spacji.

Ta podatność jest szczególnie niebezpieczna w aplikacjach internetowych polegających na ochronie przed CSRF opartej na ciasteczkach, ponieważ pozwala atakującym wstrzyknąć sfałszowane ciasteczka z tokenem CSRF, potencjalnie omijając środki bezpieczeństwa. Problem jest pogłębiony przez sposób obsługi przez Python zduplikowanych nazw ciasteczek, gdzie ostatnie wystąpienie zastępuje wcześniejsze. Podnosi to również obawy dotyczące ciasteczek __Secure- i __Host- w niebezpiecznych kontekstach oraz może prowadzić do pomijania autoryzacji, gdy ciasteczka są przekazywane do serwerów back-endowych podatnych na podszywanie.

Dodatkowe Sprawdzenia Wrażliwych Ciasteczek

Podstawowe sprawdzenia

  • Ciasteczko jest zawsze takie samo za każdym razem, gdy się logujesz.

  • Wyloguj się i spróbuj użyć tego samego ciasteczka.

  • Spróbuj zalogować się na 2 urządzeniach (lub przeglądarkach) na to samo konto, używając tego samego ciasteczka.

  • Sprawdź, czy ciasteczko zawiera jakieś informacje i spróbuj je zmodyfikować.

  • Spróbuj utworzyć kilka kont o prawie takiej samej nazwie użytkownika i sprawdź, czy można zauważyć podobieństwa.

  • Sprawdź opcję "zapamiętaj mnie", jeśli istnieje, aby zobaczyć, jak działa. Jeśli istnieje i może być podatne, zawsze używaj ciasteczka z opcji zapamiętaj mnie bez żadnego innego ciasteczka.

  • Sprawdź, czy poprzednie ciasteczko działa nawet po zmianie hasła.

Zaawansowane ataki na ciasteczka

Jeśli ciasteczko pozostaje takie samo (lub prawie takie samo) po zalogowaniu, oznacza to prawdopodobnie, że ciasteczko jest powiązane z jakimś polem twojego konta (prawdopodobnie z nazwą użytkownika). W takim przypadku możesz:

  • Spróbować utworzyć wiele kont z bardzo podobnymi nazwami użytkowników i spróbować odgadnąć, jak działa algorytm.

  • Spróbować brute force na nazwę użytkownika. Jeśli ciasteczko służy tylko jako metoda uwierzytelniania dla twojej nazwy użytkownika, możesz utworzyć konto o nazwie użytkownika "Bmin" i przeprowadzić atak brute force na każdy bit ciasteczka, ponieważ jedno z ciasteczek, które spróbujesz, będzie należeć do "admin".

  • Spróbować Padding Oracle (możesz odszyfrować zawartość ciasteczka). Użyj padbuster.

Padding Oracle - Przykłady Padbuster

padbuster <URL/path/when/successfully/login/with/cookie> <COOKIE> <PAD[8-16]>
# When cookies and regular Base64
padbuster http://web.com/index.php u7bvLewln6PJPSAbMb5pFfnCHSEd6olf 8 -cookies auth=u7bvLewln6PJPSAbMb5pFfnCHSEd6olf

# If Base64 urlsafe or hex-lowercase or hex-uppercase --encoding parameter is needed, for example:
padBuster http://web.com/home.jsp?UID=7B216A634951170FF851D6CC68FC9537858795A28ED4AAC6
7B216A634951170FF851D6CC68FC9537858795A28ED4AAC6 8 -encoding 2

Padbuster dokona kilku prób i zapyta, która z nich jest warunkiem błędu (ten, który nie jest prawidłowy).

Następnie rozpocznie deszyfrowanie ciasteczka (może to potrwać kilka minut).

Jeśli atak zakończył się sukcesem, możesz spróbować zaszyfrować wybrany ciąg znaków. Na przykład, jeśli chciałbyś zaszyfrować user=administrator

padbuster http://web.com/index.php 1dMjA5hfXh0jenxJQ0iW6QXKkzAGIWsiDAKV3UwJPT2lBP+zAD0D0w== 8 -cookies thecookie=1dMjA5hfXh0jenxJQ0iW6QXKkzAGIWsiDAKV3UwJPT2lBP+zAD0D0w== -plaintext user=administrator

To wykonanie da Ci poprawnie zaszyfrowane i zakodowane ciasteczko z ciągiem user=administrator wewnątrz.

CBC-MAC

Być może ciasteczko mogłoby mieć jakąś wartość i mogłoby być podpisane za pomocą CBC. Wtedy integralność wartości jest podpisem utworzonym za pomocą CBC z tą samą wartością. Ponieważ zaleca się użycie wektora zerowego jako IV, ten rodzaj sprawdzania integralności może być podatny na atak.

Atak

  1. Uzyskaj podpis nazwy użytkownika administ = t

  2. Uzyskaj podpis nazwy użytkownika rator\x00\x00\x00 XOR t = t'

  3. Ustaw w ciasteczku wartość administrator+t' (t' będzie poprawnym podpisem (rator\x00\x00\x00 XOR t) XOR t = rator\x00\x00\x00

ECB

Jeśli ciasteczko jest szyfrowane za pomocą ECB, może być podatne na atak. Kiedy logujesz się, otrzymywane ciasteczko musi być zawsze takie samo.

Jak wykryć i zaatakować:

Utwórz 2 użytkowników z prawie takimi samymi danymi (nazwa użytkownika, hasło, e-mail, itp.) i spróbuj odkryć jakiś wzorzec w danym ciasteczku

Utwórz użytkownika o nazwie na przykład "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa" i sprawdź, czy istnieje jakiś wzorzec w ciasteczku (ponieważ ECB szyfruje każdy blok tym samym kluczem, te same zaszyfrowane bajty mogą się pojawić, jeśli nazwa użytkownika jest zaszyfrowana).

Powinien być jakiś wzorzec (o wielkości używanego bloku). Więc, znając sposób zaszyfrowania grupy "a", możesz utworzyć nazwę użytkownika: "a"*(rozmiar bloku)+"admin". Następnie możesz usunąć zaszyfrowany wzorzec bloku "a" z ciasteczka. I będziesz miał ciasteczko użytkownika "admin".

Referencje

Try Hard Security Group

Naucz się hakować AWS od zera do bohatera z htARTE (HackTricks AWS Red Team Expert)!

Inne sposoby wsparcia HackTricks:

Last updated