# Nginx
Naucz się hakować AWS od zera do bohatera z htARTE (HackTricks AWS Red Team Expert)! Inne sposoby wsparcia HackTricks: * Jeśli chcesz zobaczyć swoją **firmę reklamowaną w HackTricks** lub **pobrać HackTricks w formacie PDF**, sprawdź [**PLANY SUBSKRYPCYJNE**](https://github.com/sponsors/carlospolop)! * Zdobądź [**oficjalne gadżety PEASS & HackTricks**](https://peass.creator-spring.com) * Odkryj [**Rodzinę PEASS**](https://opensea.io/collection/the-peass-family), naszą kolekcję ekskluzywnych [**NFT**](https://opensea.io/collection/the-peass-family) * **Dołącz do** 💬 [**Grupy Discord**](https://discord.gg/hRep4RUj7f) lub [**grupy telegramowej**](https://t.me/peass) lub **śledź** nas na **Twitterze** 🐦 [**@carlospolopm**](https://twitter.com/hacktricks\_live)**.** * **Podziel się swoimi sztuczkami hakerskimi, przesyłając PR-y do** [**HackTricks**](https://github.com/carlospolop/hacktricks) i [**HackTricks Cloud**](https://github.com/carlospolop/hacktricks-cloud) github repos.
**Natychmiastowa konfiguracja do oceny podatności i testów penetracyjnych**. Uruchom pełne testy penetracyjne z dowolnego miejsca za pomocą 20+ narzędzi i funkcji, które obejmują rozpoznanie, aż po raportowanie. Nie zastępujemy pentesterów - rozwijamy niestandardowe narzędzia, moduły wykrywania i eksploatacji, aby umożliwić im zagłębienie się głębiej, przejęcie kontroli i dobrą zabawę. {% embed url="https://pentest-tools.com/" %} ## Brakujące miejsce root ## **Podstawy konfigurowania katalogu głównego Nginx** Podczas konfigurowania serwera Nginx, dyrektywa **root** odgrywa kluczową rolę, definiując katalog bazowy, z którego są serwowane pliki. Rozważ poniższy przykład: ```bash server { root /etc/nginx; location /hello.txt { try_files $uri $uri/ =404; proxy_pass http://127.0.0.1:8080/; } } ``` W tej konfiguracji `/etc/nginx` jest określony jako katalog główny. Ta konfiguracja umożliwia dostęp do plików w określonym katalogu głównym, takich jak `/hello.txt`. Jednakże ważne jest zauważenie, że zdefiniowana jest tylko określona lokalizacja (`/hello.txt`). Brak konfiguracji dla lokalizacji głównej (`location / {...}`). Ta omissja oznacza, że dyrektywa root jest stosowana globalnie, umożliwiając żądania do ścieżki głównej `/` w celu uzyskania dostępu do plików znajdujących się w `/etc/nginx`. Z tej konfiguracji wynika istotne zagrożenie dla bezpieczeństwa. Prosty żądanie `GET`, na przykład `GET /nginx.conf`, może ujawnić poufne informacje poprzez udostępnienie pliku konfiguracyjnego Nginx znajdującego się w `/etc/nginx/nginx.conf`. Ustawienie roota na mniej wrażliwy katalog, na przykład `/etc`, może zmniejszyć to ryzyko, ale nadal może umożliwiać niezamierzony dostęp do innych istotnych plików, w tym innych plików konfiguracyjnych, logów dostępu, a nawet zaszyfrowanych poświadczeń używanych do autentykacji podstawowej protokołu HTTP. ## Konfiguracja Alias LFI W plikach konfiguracyjnych Nginx konieczna jest dokładna inspekcja dyrektyw "location". Podatność znana jako Local File Inclusion (LFI) może zostać nieumyślnie wprowadzona poprzez konfigurację, która przypomina poniższy przykład: ``` location /imgs { alias /path/images/; } ``` Ta konfiguracja jest podatna na ataki LFI, ponieważ serwer interpretuje żądania takie jak `/imgs../flag.txt` jako próbę dostępu do plików spoza zamierzonego katalogu, efektywnie rozwiązując się do `/path/images/../flag.txt`. Ta wada pozwala atakującym na pobieranie plików z systemu plików serwera, do których nie powinno być dostępu przez sieć. Aby złagodzić tę podatność, konfiguracja powinna zostać dostosowana do: ``` location /imgs/ { alias /path/images/; } ``` Więcej informacji: [https://www.acunetix.com/vulnerabilities/web/path-traversal-via-misconfigured-nginx-alias/](https://www.acunetix.com/vulnerabilities/web/path-traversal-via-misconfigured-nginx-alias/) Testy Accunetix: ``` alias../ => HTTP status code 403 alias.../ => HTTP status code 404 alias../../ => HTTP status code 403 alias../../../../../../../../../../../ => HTTP status code 400 alias../ => HTTP status code 403 ``` ## Niebezpieczne ograniczenie ścieżki Sprawdź następującą stronę, aby dowiedzieć się, jak ominąć dyrektywy takie jak: ```plaintext location = /admin { deny all; } location = /admin/ { deny all; } ``` ## Niestabilne użycie zmiennej / Podział żądania HTTP {% hint style="danger" %} Narażone zmienne `$uri` i `$document_uri` mogą zostać naprawione poprzez ich zastąpienie przez `$request_uri`. Regex może również być podatne, na przykład: `location ~ /docs/([^/])? { … $1 … }` - Narażone `location ~ /docs/([^/\s])? { … $1 … }` - Niepodatne (sprawdzanie spacji) `location ~ /docs/(.*)? { … $1 … }` - Niepodatne {% endhint %} Przykład podatności w konfiguracji Nginx jest przedstawiony poniżej: ``` location / { return 302 https://example.com$uri; } ``` Znaki \r (powrót karetki) i \n (nowa linia) oznaczają nowe znaki w żądaniach HTTP, a ich zaszyfrowane w formie URL są reprezentowane jako `%0d%0a`. Włączenie tych znaków w żądaniu (np. `http://localhost/%0d%0aDetectify:%20clrf`) do źle skonfigurowanego serwera skutkuje wydaniem przez serwer nowego nagłówka o nazwie `Detectify`. Dzieje się tak, ponieważ zmienna $uri dekoduje zaszyfrowane w formie URL znaki nowej linii, co prowadzi do nieoczekiwanego nagłówka w odpowiedzi: ``` HTTP/1.1 302 Moved Temporarily Server: nginx/1.19.3 Content-Type: text/html Content-Length: 145 Connection: keep-alive Location: https://example.com/ Detectify: clrf ``` Dowiedz się więcej o ryzyku wstrzykiwania CRLF i podziału odpowiedzi na [https://blog.detectify.com/2019/06/14/http-response-splitting-exploitations-and-mitigations/](https://blog.detectify.com/2019/06/14/http-response-splitting-exploitations-and-mitigations/). Ta technika jest również [**wyjaśniona w tej prezentacji**](https://www.youtube.com/watch?v=gWQyWdZbdoY\&list=PL0xCSYnG\_iTtJe2V6PQqamBF73n7-f1Nr\&index=77) z przykładami podatności i mechanizmami wykrywania. Na przykład, aby wykryć tę konfigurację z perspektywy blackbox, można użyć tych żądań: * `https://example.com/%20X` - Dowolny kod HTTP * `https://example.com/%20H` - 400 Bad Request Jeśli jest podatny, pierwsze żądanie zwróci "X", ponieważ "X" to dowolna metoda HTTP, a drugie spowoduje błąd, ponieważ "H" nie jest poprawną metodą. Serwer otrzyma coś w rodzaju: `GET / H HTTP/1.1`, co spowoduje błąd. Inne przykłady wykrywania to: * `http://company.tld/%20HTTP/1.1%0D%0AXXXX:%20x` - Dowolny kod HTTP * `http://company.tld/%20HTTP/1.1%0D%0AHost:%20x` - 400 Bad Request Niektóre znalezione podatne konfiguracje przedstawione w tej prezentacji to: * Zauważ, jak **`$uri`** jest ustawione tak, jak jest w końcowym adresie URL. ``` location ^~ /lite/api/ { proxy_pass http://lite-backend$uri$is_args$args; } ``` * Zauważ, jak ponownie **`$uri`** znajduje się w adresie URL (tym razem wewnątrz parametru) ``` location ~ ^/dna/payment { rewrite ^/dna/([^/]+) /registered/main.pl?cmd=unifiedPayment&context=$1&native_uri=$uri break; proxy_pass http://$back; ``` * Teraz w AWS S3 ``` location /s3/ { proxy_pass https://company-bucket.s3.amazonaws.com$uri; } ``` ### Dowolna zmienna Odkryto, że **dane dostarczone przez użytkownika** mogą być traktowane jako **zmienna Nginx** w określonych okolicznościach. Przyczyna tego zachowania pozostaje w pewnym stopniu niejasna, ale nie jest rzadka ani łatwa do zweryfikowania. To anomalie zostało podkreślone w raporcie bezpieczeństwa na HackerOne, który można zobaczyć [tutaj](https://hackerone.com/reports/370094). Dalsze dochodzenie w sprawie komunikatu o błędzie doprowadziło do zidentyfikowania jego występowania w [module filtru SSI kodu źródłowego Nginx](https://github.com/nginx/nginx/blob/2187586207e1465d289ae64cedc829719a048a39/src/http/modules/ngx_http_ssi_filter_module.c#L365), wskazując na Server Side Includes (SSI) jako główną przyczynę. Aby **wykryć tę błędną konfigurację**, można wykonać następujące polecenie, które polega na ustawieniu nagłówka referer w celu przetestowania drukowania zmiennej: ```bash $ curl -H ‘Referer: bar’ http://localhost/foo$http_referer | grep ‘foobar’ ``` Skanowania dla tej konfiguracji na różnych systemach ujawniły wiele przypadków, gdzie zmienne Nginx mogły być wydrukowane przez użytkownika. Jednak spadek liczby podatnych przypadków sugeruje, że wysiłki w celu załatania tego problemu były do pewnego stopnia skuteczne. ## Odczyt surowej odpowiedzi z backendu Nginx oferuje funkcję poprzez `proxy_pass`, która pozwala na przechwytywanie błędów i nagłówków HTTP generowanych przez backend, mając na celu ukrycie wewnętrznych komunikatów o błędach i nagłówków. Jest to osiągane poprzez serwowanie Nginx niestandardowych stron błędów w odpowiedzi na błędy backendu. Jednak pojawiają się wyzwania, gdy Nginx napotyka nieprawidłowe żądanie HTTP. Takie żądanie jest przekazywane do backendu w otrzymanej postaci, a surowa odpowiedź backendu jest następnie bezpośrednio wysyłana do klienta bez interwencji Nginx. Rozważmy przykładowy scenariusz dotyczący aplikacji uWSGI: ```python def application(environ, start_response): start_response('500 Error', [('Content-Type', 'text/html'), ('Secret-Header', 'secret-info')]) return [b"Secret info, should not be visible!"] ``` Aby to zarządzać, używane są konkretne dyrektywy w konfiguracji Nginx: ``` http { error_page 500 /html/error.html; proxy_intercept_errors on; proxy_hide_header Secret-Header; } ``` * [**proxy\_intercept\_errors**](http://nginx.org/en/docs/http/ngx\_http\_proxy\_module.html#proxy\_intercept\_errors): Ta dyrektywa umożliwia Nginxowi obsługę niestandardowej odpowiedzi dla odpowiedzi z backendu z kodem stanu większym niż 300. Zapewnia, że dla naszej przykładowej aplikacji uWSGI odpowiedź `500 Error` jest przechwytywana i obsługiwana przez Nginx. * [**proxy\_hide\_header**](http://nginx.org/en/docs/http/ngx\_http\_proxy\_module.html#proxy\_hide\_header): Jak sugeruje nazwa, ta dyrektywa ukrywa określone nagłówki HTTP przed klientem, poprawiając prywatność i bezpieczeństwo. Gdy zostanie wysłane prawidłowe żądanie `GET`, Nginx przetwarza je normalnie, zwracając standardową odpowiedź błędu, nie ujawniając żadnych poufnych nagłówków. Jednakże nieprawidłowe żądanie HTTP omija ten mechanizm, co skutkuje ujawnieniem surowych odpowiedzi z backendu, w tym poufnych nagłówków i komunikatów błędów. ## merge\_slashes ustawione na off Domyślnie dyrektywa **`merge_slashes`** Nginxa jest ustawiona na **`on`**, co kompresuje wiele ukośników w przekierowaniu URL do pojedynczego ukośnika. Ta funkcja, podczas upraszczania przetwarzania URL, może niechcący ukrywać podatności w aplikacjach za Nginx, zwłaszcza tych podatnych na ataki lokalnego dołączania plików (LFI). Eksperci ds. bezpieczeństwa **Danny Robinson i Rotem Bar** zwrócili uwagę na potencjalne ryzyko związane z tym domyślnym zachowaniem, zwłaszcza gdy Nginx działa jako odwrotny proxy. Aby zmniejszyć takie ryzyko, zaleca się **wyłączenie dyrektywy `merge_slashes`** dla aplikacji podatnych na te podatności. Zapewnia to, że Nginx przekazuje żądania do aplikacji bez zmiany struktury URL, nie maskując żadnych istniejących problemów z bezpieczeństwem. Aby uzyskać więcej informacji, sprawdź [Danny Robinson i Rotem Bar](https://medium.com/appsflyer/nginx-may-be-protecting-your-applications-from-traversal-attacks-without-you-even-knowing-b08f882fd43d). ### **Wartość domyślna w dyrektywie Map** W konfiguracji Nginx, dyrektywa `map` często odgrywa rolę w **kontroli autoryzacji**. Powszechnym błędem jest nieokreślenie **wartości domyślnej**, co może prowadzić do nieautoryzowanego dostępu. Na przykład: ```yaml http { map $uri $mappocallow { /map-poc/private 0; /map-poc/secret 0; /map-poc/public 1; } } ``` ```yaml server { location /map-poc { if ($mappocallow = 0) {return 403;} return 200 "Hello. It is private area: $mappocallow"; } } ``` Bez `default`, **złośliwy użytkownik** może ominąć zabezpieczenia, uzyskując dostęp do **niezdefiniowanego URI** wewnątrz `/map-poc`. [Podręcznik Nginx](https://nginx.org/en/docs/http/ngx_http_map_module.html) zaleca ustawienie **wartości domyślnej**, aby uniknąć takich problemów. ### **Podatność na DNS Spoofing** Podatność na DNS spoofing w przypadku Nginx jest wykonalna w określonych warunkach. Jeśli atakujący zna **serwer DNS** używany przez Nginx i może przechwycić jego zapytania DNS, może sfałszować rekordy DNS. Metoda ta jednak nie działa, jeśli Nginx jest skonfigurowany do korzystania z **localhost (127.0.0.1)** do rozwiązywania nazw DNS. Nginx pozwala określić serwer DNS w następujący sposób: ```yaml resolver 8.8.8.8; ``` ### **Dyrektywy `proxy_pass` i `internal`** Dyrektywa **`proxy_pass`** jest wykorzystywana do przekierowywania żądań do innych serwerów, zarówno wewnętrznie, jak i zewnętrznie. Dyrektywa **`internal`** zapewnia, że określone lokalizacje są dostępne tylko w obrębie Nginx. Chociaż te dyrektywy same w sobie nie stanowią podatności, ich konfiguracja wymaga dokładnego zbadania, aby zapobiec lukom w zabezpieczeniach. ## proxy\_set\_header Upgrade & Connection Jeśli serwer nginx jest skonfigurowany do przekazywania nagłówków Upgrade i Connection, atak [**h2c Smuggling**](../../pentesting-web/h2c-smuggling.md) może zostać przeprowadzony w celu uzyskania dostępu do chronionych/wewnętrznych punktów końcowych. {% hint style="danger" %} Ta podatność pozwoliłaby atakującemu **ustanowić bezpośrednie połączenie z punktem końcowym `proxy_pass`** (`http://backend:9999` w tym przypadku), którego zawartość nie zostanie sprawdzona przez nginx. {% endhint %} Przykład podatnej konfiguracji do kradzieży `/flag` znajdziesz [tutaj](https://bishopfox.com/blog/h2c-smuggling-request): ``` server { listen 443 ssl; server_name localhost; ssl_certificate /usr/local/nginx/conf/cert.pem; ssl_certificate_key /usr/local/nginx/conf/privkey.pem; location / { proxy_pass http://backend:9999; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection $http_connection; } location /flag { deny all; } ``` {% hint style="warning" %} Zauważ, że nawet jeśli `proxy_pass` wskazywał na określoną **ścieżkę**, taką jak `http://backend:9999/socket.io`, połączenie zostanie nawiązane z `http://backend:9999`, więc możesz **skontaktować się z dowolną inną ścieżką wewnątrz tego wewnętrznego punktu końcowego. Dlatego nie ma znaczenia, czy ścieżka jest określona w adresie URL proxy\_pass.** {% endhint %} ## Wypróbuj to samodzielnie Detectify stworzył repozytorium na GitHubie, gdzie możesz użyć Dockera, aby skonfigurować własny podatny serwer testowy Nginx z niektórymi błędami konfiguracyjnymi omówionymi w tym artykule i spróbować je znaleźć samodzielnie! [https://github.com/detectify/vulnerable-nginx](https://github.com/detectify/vulnerable-nginx) ## Narzędzia do analizy statycznej ### [GIXY](https://github.com/yandex/gixy) Gixy to narzędzie do analizy konfiguracji Nginx. Głównym celem Gixy jest zapobieganie błędom konfiguracji związanych z bezpieczeństwem i automatyzacja wykrywania wad. ### [Nginxpwner](https://github.com/stark0de/nginxpwner) Nginxpwner to proste narzędzie do wyszukiwania powszechnych błędów konfiguracyjnych i podatności Nginx. ## Odnośniki * [**https://blog.detectify.com/2020/11/10/common-nginx-misconfigurations/**](https://blog.detectify.com/2020/11/10/common-nginx-misconfigurations/) * [**http://blog.zorinaq.com/nginx-resolver-vulns/**](http://blog.zorinaq.com/nginx-resolver-vulns/) * [**https://github.com/yandex/gixy/issues/115**](https://github.com/yandex/gixy/issues/115)
**Natychmiastowa dostępność konfiguracji do oceny podatności i testów penetracyjnych**. Uruchom pełny test penetracyjny z dowolnego miejsca za pomocą ponad 20 narzędzi i funkcji, które obejmują rozpoznanie, raportowanie. Nie zastępujemy pentesterów - rozwijamy niestandardowe narzędzia, moduły wykrywania i eksploatacji, aby umożliwić im zagłębienie się głębiej, zdobycie dostępu i dobrą zabawę. {% embed url="https://pentest-tools.com/" %}
Dowiedz się, jak hakować AWS od zera do bohatera z htARTE (HackTricks AWS Red Team Expert)! Inne sposoby wsparcia HackTricks: * Jeśli chcesz zobaczyć swoją **firmę reklamowaną w HackTricks** lub **pobrać HackTricks w formacie PDF**, sprawdź [**PLANY SUBSKRYPCYJNE**](https://github.com/sponsors/carlospolop)! * Zdobądź [**oficjalne gadżety PEASS & HackTricks**](https://peass.creator-spring.com) * Odkryj [**Rodzinę PEASS**](https://opensea.io/collection/the-peass-family), naszą kolekcję ekskluzywnych [**NFT**](https://opensea.io/collection/the-peass-family) * **Dołącz do** 💬 [**grupy Discord**](https://discord.gg/hRep4RUj7f) lub [**grupy telegramowej**](https://t.me/peass) lub **śledź** nas na **Twitterze** 🐦 [**@carlospolopm**](https://twitter.com/hacktricks\_live)**.** * **Podziel się swoimi sztuczkami hakerskimi, przesyłając PR do** [**HackTricks**](https://github.com/carlospolop/hacktricks) i [**HackTricks Cloud**](https://github.com/carlospolop/hacktricks-cloud) github repos.